shanjayp
shanjayp
Published on 2025-02-14 / 4 Visits
0
0

3. Shell脚本字符串处理

在shell环境中,将一些需要重复使用的操作,定义为公共的语句块,即可称为函数(给一堆命令取一个别名)

函数可以使脚本中的代码更加简洁,增强易读性,提高脚本的执行效率

#函数定义格式1
function 函数名 {
    执行的命令1
    执行的命令2
    ...省略更多命令
}
​
#函数定义格式2
函数名() {
    执行的命令1
    执行的命令2
    ...省略更多命令
}
​
#定义函数
#!/bin/bash
net() {
ifconfig ens32 | grep "RX packets"
ifconfig ens32 | grep "TX packets"
}
​
while :
do
        clear
        net   #调用函数
        sleep 1
done
​
​
​
#定义Nginx status页面
ngx_status="http://127.0.0.1/status"
​
#判断status页面是否存活
ngx_status_code() {
        http_code=`curl -o /dev/null -s -w %{http_code} ${ngx_status}`
        if [ ${http_code} == "200" ];then
                return 1
        else
                echo "Nginx status is not running."
        fi
}
​
#获取当前活动的客户端连接数
active() {
        ngx_status_code || curl -s ${ngx_status} | grep "Active" | awk '{print $NF}'
}
​
#获取接收客户端连接的总数量
accepts() {
        ngx_status_code || curl -s ${ngx_status} | awk NR==3 | awk '{print $1}'
}
​
#获取已处理的连接总数量
handled() {
        ngx_status_code || curl -s ${ngx_status} | awk NR==3 | awk '{print $2}'
}
​
#获取客户端请求总数量
requests() {
        ngx_status_code || curl -s ${ngx_status} | awk NR==3 | awk '{print $3}'
}
​
#获取正在读取请求标头的当前连接数量
reading() {
        ngx_status_code || curl -s ${ngx_status} | grep "Reading" | awk '{print $2}'
}
​
#获取正在将响应写回到客户端的当前连接数量
writing() {
        ngx_status_code || curl -s ${ngx_status} | grep "Writing" | awk '{print $2}'
}
​
#获取当前正在等待响应的客户端连接数量
waiting() {
        ngx_status_code || curl -s ${ngx_status} | grep "Waiting" | awk '{print $2}'
}
​
#使用位置变量控制脚本输出
case $1 in
        active)
                active;;
        accepts)
                accepts;;
        handled)
                handled;;
        requests)
                requests;;
        reading)
                reading;;
        writing)
                writing;;
        waiting)
                waiting;;
        *)
                echo "Unknown options"
esac
​
​
​
#fork炸弹
vim fork.sh 
#!/bin/bash
.() {
.|. &
}
.
​
​
chmod u+x fork.sh 
./fork.sh 

脚本中断及退出

  • break #结束整个循环

  • continue #结束本次循环,进入下一次循环

  • exit #退出脚本

#例子
​
#!/bin/bash
for i in {1..5}
do
        echo $i
done
echo Over
​
#跳过第三次循环,进入下一次循环
​
​
#结束第三次循环,进入下一次循环
#!/bin/bash
for i in {1..5}
do
        [ $i -eq 3 ] && continue
        echo $i
done
echo Over
​
./for1.sh 
1
2
4
5
Over
​
​
#结束整个循环
#!/bin/bash
for i in {1..5}
do
        [ $i -eq 3 ] && break
        echo $i
done
echo Over
​
./for1.sh 
1
2
Over
​
#直接退出脚本
vim for1.sh
#!/bin/bash
for i in {1..5}
do
        [ $i -eq 3 ] && exit
        echo $i
done
echo Over
​
./for1.sh 
1
2

字符串截取

在使用shell脚本完成各种运维任务时,一旦涉及到判断、条件测试等相关操作时往往需要对相关的命令输出进行过滤,提取出符合要求的字符串

  • 字符串截取的常用方法:${变量名:起始位置:长度}

  • ${}截取字符串时,起始位置是从0开始的

phone=13812345678
​
echo $phone
13812345678
​
#统计变量的个数
echo ${#phone}
11
​
#截取变量的前三位,在截取时包含数字本身
 echo ${phone:0:3}
138
​
#截取后四位
echo ${phone:7:4}
5678
​
#截取中间四位
echo ${phone:3:4}
1234
​
​
#截取一个随机的8位密码
pass=qwertyuiopasdfghjklzxcvbnmQWERTYUIOPASDFGHJKLZXCVBNM0123456789
for i in {1..8}
do
        num=$[RANDOM%62]
        num1=${pass:num:1}
        num2=$num2$num1
done
echo $num2

字符串替换

只替换第一个匹配的结果:${变量名/xx/yy}

替换全部匹配的结果:${变量名//xx/yy}

#只替换匹配到的第一个字符
echo $phone
13812345678
​
#将匹配到的第一个3替换成4
echo ${phone/3/4}
14812345678  
​
#将匹配到的所有3替换成4
echo ${phone//3/4}
14812445678

字符串掐头去尾

  • 从左向右,最短匹配删除:${变量名#*关键词}

  • 从左向右,最长匹配删除:${变量名##*关键词}

  • 从右向左,最短匹配删除:${变量名%关键词*}

  • 从右向左,最长匹配删除:${变量名%%关键词*}

#定义素材
x=`head -1 /etc/passwd`
[root@localhost yunwei]# echo $x
root:x:0:0:root:/root:/bin/bash
​
#从左到右最短匹配
echo ${x#root}
​
​
#从左到右最短匹配,不加*只匹配最左侧的字串
 echo ${x#0}
​
​
#从左到右最短匹配,加*匹配遇到的第一个字串
echo ${x#*0}
​
​
#从左到右最长匹配
echo ${x##0}
root:x:0:0:root:/root:/bin/bash
​
#从左到右最长匹配
echo ${x##*0}
:root:/root:/bin/bash
​
#从右到做最短匹配
echo ${x%/bash}
root:x:0:0:root:/root:/bin
​
#从右到做最短匹配
echo ${x%root*}
root:x:0:0:root:/
​
#从右向左最长匹配
echo ${x%%root*}
​
#从右向左最短匹配
echo ${x%0*}
root:x:0:
​
#从右向左最长匹配
echo ${x%%0*}
root:x:
​
#把文件以.doc结尾的扩展名,全部改为.txt
touch {1..100}.doc
​
​
#字符串去尾方式批量修改文件扩展名
vim file.sh 
#!/bin/bash
for i in `ls *.doc`
do
        mv $i ${i%doc}txt
done
​
#字符串替换方式批修改文件扩展名
vim file.sh 
#!/bin/bash
for i in `ls *.txt`
do
        mv $i ${i/txt/doc}
done

shell数组

#定义数组方式一:数组名=(值1 值2 值3 .. .. 值n)
phone=(13112345678 13212345678 13412345678 13512345678 13612345678)
​
​
#按照下标取值,下标从0起使,0就是数组内的第一个值
echo ${x[0]}
echo ${x[0]}
echo ${x[1]}
echo ${x[2]}
echo ${x[3]}
echo ${x[4]}
​
#获取数组内所有值
echo ${x[@]}
echo ${x[*]}
​
#向数组内赋值:数组名[下标]=值
phone[5]=13812345678
echo ${b[*]}
​
​
#通过数组下载软件包
vim yum.sh
#!/bin/bash
x=(vsftpd httpd gcc openssl-devel pcre-devel)
for i in ${x[@]}
do
        yum -y install $i
done

正则表达式

正则表达式使用一串符号描述有共同属性的数据

基本正则符号

描述

^

匹配行首

$

匹配行尾

[]

集合,匹配集合中的任意单个字符

[^]

对集合取反

.

匹配任意单个字符

*

匹配前一个字符出现的任意次数

#匹配以什么什么开头的行
grep "^root" /etc/passwd
grep "^#" /etc/fstab
​
#匹配以什么什么结尾的行
grep "bash$" /etc/passwd
​
#排除
grep -v "^#" /etc/fstab
grep -v "^#" /etc/fstab | grep -v "^$" 
​
#集合,匹配集合中的任意单个字符
grep "ro[abcotabcd]" /etc/passwd
​
#集合,对集合中的任意单个字符取反
grep "ro[^abcotabcd]" /etc/passwd
​
​
#匹配任意单个字符
grep "roo." /etc/passwd
grep ".oot" /etc/passwd
grep "w.*" /etc/passwd

扩展正则符号

描述

|

或者

#或者
egrep "root|bash" /etc/passwd
netstat -ntlp | egrep "22|80"



Comment