avatar

2.Shell脚本的条件测试与比较

Shell条件表达式与整数比较

第1章 常用的条件表达式

语法 意义
test -f file 表示如果file文件存在,则为真(0),否则为假(非0)
test -z 表示如果字符串长度是为0,则表达式成立
[ -e file ] 文件存在则为真
[ -f file ] 是否存在并且为普通文件
[ -d file ] 是否为目录
[ -r file ] 是否可读
[ -w file ] 是否可写
[ -x file ] 是否可执行

1.1 test

1
2
#如果file文件存在,则输出true,否则则输出false
test -f file && echo true || echo false

用test -z 来测试字符段长度是否为0

1
2
[root@backup ~]# test -z "oldboy" && echo 1||echo 0
0

1.2 []

1
2
3
4
5
6
7
8
9
10
11
12
[root@backup ~]# [ -e /etc ] && echo "文件存在"||echo "文件不存在"
文件存在
[root@backup ~]# [ -e /etc/hosts ] && echo "文件存在"||echo "文件不存在"
文件存在
[root@backup ~]# [ -e /etcccc ] && echo "文件存在"||echo "文件不存在"
文件不存在
[root@backup ~]# [ -f /etcccc ] && echo "文件存在"||echo "文件不存在"
文件不存在
[root@backup ~]# [ -f /etc ] && echo "文件存在"||echo "文件不存在"
文件不存在
[root@backup ~]# [ -f /etc/passwd ] && echo "文件存在"||echo "文件不存在"
文件存在

案例:

1
# [ -f /etc/init.d/functions ] && source /etc/init.d/functions
1
2
3
4
5
6
7
8
9
10
11
12
13
[root@backup ~]# [ -d /etc/passwd ] && echo "文件存在"||echo "文件不存在"
文件不存在
[root@backup ~]# [ -d /etc/ ] && echo "文件存在"||echo "文件不存在"
文件存在
[root@backup ~]# [ ! -d /etc/ ] && echo "文件存在"||echo "文件不存在"
文件不存在
[root@backup ~]# [ -d /etc/ ] && echo "文件存在"||echo "文件不存在"
文件存在
[root@backup ~]# [ -d /etcc ] && echo "文件存在"||echo "文件不存在"
文件不存在
[root@backup ~]# [ ! -d /etccc ] && mkdir /etccc
[root@backup ~]# [ -x /etc/shadow ] && echo "可读" || echo "不可读"
不可读

案例: 如果目录不存在则创建

1
2
3
[root@backup ~]# [ -d /etcc ] || mkdir /etcc
[root@backup ~]# ll /etcc
total 0

1.3 [[]] 正则

[[]]与[]的区别:

[[]]中可以使用通配符进行匹配

1
# [[ -f /tmp/oldboy.txt ]] && echo 1 || echo 0

第2章 数值表达式

整数比较

[ 整数1 比较符 整数2 ]

在[]以及test 中使用的比较符号 在(())和[[]] 中使用的比较符号 说明
-eq == 或 = 等于
-ne != 不等于
-gt > 大于
-ge >= 大于等于
-lt < 小于
-le <= 小于等于

2.1 []

具体实例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
[root@backup ~]# [ 10 -eq 10 ] && echo "成立" || echo "不成立"
成立
[root@backup ~]# [ 10 -gt 10 ] && echo "成立" || echo "不成立"
不成立
[root@backup ~]# [ 10 -ge 10 ] && echo "成立" || echo "不成立"
成立
[root@backup ~]# [ 10 -le 10 ] && echo "成立" || echo "不成立"
成立
[root@backup ~]# [ 11 -le 10 ] && echo "成立" || echo "不成立"
不成立
[root@backup ~]# [ 11 -ne 10 ] && echo "成立" || echo "不成立"
成立
[root@backup ~]# [ 11 -gt 10 ] && echo "成立" || echo "不成立"
成立
[root@backup ~]# [ 11 -gt 100 ] && echo "成立" || echo "不成立"
不成立
[root@backup ~]# [ 11 -lt 100 ] && echo "成立" || echo "不成立"
成立
[root@backup ~]# [ 11 -ne 100 ] && echo "成立" || echo "不成立"
成立

2.2 (()) [[]]

1
2
3
4
5
6
=或==
>
>=
<
<=
1=

案例: 统计磁盘使用率 如果磁盘使用率大于 5% 则发邮件报警 当前使用率为? 小于5% 则提示磁盘使用正常 当前使用率为?

1
2
3
4
5
6
7
8
[root@backup /server/scripts]# cat disk.sh 
#!/bin/sh
usedisk=`df -h|awk 'NR==2{print $(NF-1)}'`
[ ${usedisk%\%} -gt 80 ] && echo "send mail 当前使用为$usedisk" || echo "磁盘使用正常,当前使用率为$usedisk"
[ `df -h|awk -F "[ %]+" 'NR==2{print $(NF-1)}'` -gt 5 ] && echo "send mail" || echo "磁盘使用正常"
[root@backup /server/scripts]# sh disk.sh
磁盘使用正常,当前使用率为4%
磁盘使用正常

案例2: 统计内存使用率 如果大于5% 发邮件 小于5 提示正常

  1. 如何查看使用率 并取出数值 计算百分比 使用/总的*100
  2. 如何做比较 [ ]
  3. 如何输出内容
  4. 测试
1
2
[root@backup /server/scripts]# [ `free|awk 'NR==2{print $3/$2*100}'|awk -F. '{print $1}'` -gt 11 ] && echo "send mail"|| echo ok
ok

案例3: 统计系统负载 负载超过2则发邮件 小于1则正常

1
2
3
4
ab -n 500000 -c 20000 http://127.0.0.1/index.html
加大文件描述符
echo '* - nofile 65535'>>/etc/security/limits.conf
重新打开窗口

案例4:使用脚本 统计系统的 主机名 IP地址 虚拟平台 版本号 磁盘使用率 内存使用率 外网IP地址

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
[root@backup /server/scripts]# cat os.sh 
#!/bin/bash
eth0=$(ip a|awk 'BEGIN{FS="[ /]+"}/eth0$/{print $3}')
eth1=$(ip a|awk 'BEGIN{FS="[ /]+"}/eth1$/{print $3}')
net_IP=$(curl -s ifconfig.me) # 或者 curl icanhazip.com
VMW=$(hostnamectl | awk '/Virtuali/{print $NF}')
version=$(awk '{print $1,$(NF-1)}' /etc/redhat-release)
disk=$(df|awk 'NR==2{print $(NF-1)}')
mem="$(free|awk 'NR==2{print $3/$2*100}')%"
echo "内网IP为:${eth0}"
echo "外网IP为:${eth1}"
echo "公网IP为:${net_IP}"
echo "虚拟平台为:${VMW}"
echo "操作系统为:${version}"
echo "磁盘使用率为:${disk}"
echo "内存使用率为:${mem}"
[root@backup /server/scripts]# sh os.sh
内网IP为:10.0.1.41
外网IP为:172.16.1.41
公网IP为:113.88.12.225
虚拟平台为:vmware
操作系统为:CentOS 7.4.1708
磁盘使用率为:4%
内存使用率为:10.2867%

第3章 多整数比较

在[] 和 test 中使用的符号 在[[]] 和 (()) 中使用的符号 说明
-a && and 与,两端都为真,则结果为真
-o || or 或,两端有一个为真,则为真
! ! not 非,两端相反为真,则结果为真
1
2
[ 整数1 比较符 整数2 -o 整数3 比较符 整数4 ]
[ 整数1 比较符 整数2 -a 整数3 比较符 整数4 ]
1
2
3
4
5
6
[root@backup ~]# [ 10 -eq 10 -o 100 -ne 100 ]
[root@backup ~]# echo $?
0
[root@backup ~]# [ 10 -eq 10 -a 100 -ne 100 ]
[root@backup ~]# echo $?
1

案例:反向破解 RANDOM 0-32767

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
案例:反向破解 RANDOM 0-32767
d2c74151
a9982990
4462a9fd
b195fe48
5e77d38
[root@backup /server/scripts]# cat RANDOM.sh
#!/bin/bash
for i in {0..32767}
do
num1=`echo $i|md5sum|cut -c1-8`
[ $num1 = "d2c74151" -o $num1 = "a9982990" -o $num1 = "4462a9fd" -o $num1 = "b195fe48" ];
[ $? = 0 ] && echo "$num1 is $i"
num2=`echo $i|md5sum|cut -c1-7`
[ $num2 = "5e77d38" ];[ $? = 0 ] && echo "$num2 is $i"
done
[root@backup /server/scripts]# sh RANDOM.sh
4462a9fd is 2458
5e77d38 is 2945
d2c74151 is 6420
a9982990 is 13008
b195fe48 is 29193

第4章 字符串比较

字符串比较 必须加双引号

1
2
3
[root@backup ~]# [ "$USER" = root ]
[root@backup ~]# echo $?
0

-z 值为0 则为真
-n 值不为0 则为真

1
2
3
4
5
6
7
8
9
10
11
[root@backup ~]# echo $?
0
[root@backup ~]# name=alex
[root@backup ~]# echo $name
alex
[root@backup ~]# [ -z $name ]
[root@backup ~]# echo $?
1
[root@backup ~]# [ -n $name ]
[root@backup ~]# echo $?
0

案例: 判断传参是否为空

1
2


第5章 正则比对

正则比对 [[]]
取反 ! 写在表达式的前面

1
2
3
4
5
6
7
8
[root@backup /server/scripts]# [ "$USER" =~ ^r ]
-bash: [: =~: binary operator expected
[root@backup /server/scripts]# [[ "$USER" =~ ^r ]] #必须[[]]
[root@backup /server/scripts]# echo $?
0
[root@backup /server/scripts]# [[ ! "$USER" =~ ^n ]] #取反卸载最前面
[root@backup /server/scripts]# echo $?
0

判断数字是否为整数

1
[[ "$num" =~ ^[0-9]+$ ]]

案例: 使用read 传参方式 传入两个数字 做比较 大了则提示大了 小了则提示小了 等于则等于=
禁止使用if

1
2




文章作者: Wu Fei
文章链接: http://linuxwf.com/2020/04/15/2-Shell%E8%84%9A%E6%9C%AC%E7%9A%84%E6%9D%A1%E4%BB%B6%E6%B5%8B%E8%AF%95%E4%B8%8E%E6%AF%94%E8%BE%83/
版权声明: 本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来自 WF's Blog
打赏
  • 微信
    微信
  • 支付宝
    支付宝

评论