目录
引言
一、条件测试
1、文件测试与整数测试
(1)test命令
(2)文件测试
(3)整数测试
2、字符串测试与逻辑测试
(1)字符串测试
(2)逻辑测试
二、if语句
1、if单分支语句
(1)单分支的结构
(2)单分支if语句的语法格式
(3)单分支if语句的结构图
2、if双分支语句
(1)双分支的结构
(2)双分支if语句的语法格式
(3)双分支if语句的结构图
3、if多分支语句
(1)多分支的结构
(2)多分支if语句的语法格式
(3)多分支if语句的结构图
三、case语句
1、case多分支结构
2、case多分支语句的语法格式
3、case多分支语句的结构图
总结
在处理Linux系统任务的时候,往往使用单一的顺序结构的脚本过于太慢,不够智能化,难以处理更难的系统任务,给管理人员带来很大的工作量,而从引用到if语句和case语句,就能够批量的实现系统任务,实现智能化,提高管理员的工作效率。
测试表达式是否成立,若成立返回0,否则返回其他数值。
①格式1:test 条件表达式
②格式2:[ 条件表达式 ]
①文件测试指的是根据给定的路径名称,判断对应的是文件还是目录,或者判断文件是否可读、可写、可执行等。文件测试的常见操作选项如下,使用时将测试对象放在操作选项之后即可。
[ 操作符 文件或目录 ]
②常用的测试操作符
-d:测试是否为目录(Directory)。
-e:测试目录或文件是否存在(Exist)。
-f:测试是否为文件(File)。
-r:测试当前用户是否有权限读取(Read)。
-w:测试当前用户是否有权限写入(write)。
-x:测试是否设置有可执行(Excute)权限。
-b:测试是否为设备文件。
-c:测试是否为字符设备文件。
-s:测试存在且文件大小为空。
-L:测试是否为链接文件。
执行条件测试操作以后,通过预定义变量$?可以获得测试命令的返回状态值,从而判断该条件是否成立。
执行以下操作可测试目录/media/是否存在,如果返回值$?为0,表示存在此目录,否则表示不存在,或者虽然存在但不是目录。
[root@localhost ~]# test -d /etc/sysconfig/ && echo "测试的结果是目录"
测试的结果是目录
[root@localhost ~]# test -f /etc/sysconfig/ || echo "测试的结果不文件"
测试的结果不文件
[root@localhost ~]# test -e /etc/sysconfig/ && echo "测试的结果是目录"
测试的结果是目录
[root@localhost ~]# echo $?
[root@localhost ~]# [ -d /home/admin/ ]
[root@localhost ~]# echo $?
1
[root@localhost ~]# useradd admin
[root@localhost ~]# [ -d /home/admin/ ] && echo "yes"
yes
[root@localhost ~]# echo $?
0
[root@localhost ~]# [ ! -e /opt/xm/ ] && mkdir /opt/xm/
[root@localhost ~]# echo $?
0
[root@localhost ~]# ls /opt/
rh xm
①整数值比较指的是根据给定的两个整数值,判断第一个数与第二个数的关系,如是否大于、等于、小于第二个数。整数值比较的常用操作选项如下,使用时将操作选项放在要比较的两个整数之间。
[ 整数1 操作符 整数2 ]
②常用的测试操作符
-eq:第一个数等于(Equal)第二个数。
-ne:第一个数不等于(Not Equal)第二个数。
-gt:第一个数大于(Greater Than)第二个数。
-lt:第一个数小于(Lesser Than)第二个数。
-le:第一个数小于或等于(Lesser or Equal)第二个数。
-ge:第一个数大于或等于(Greater or Equal)第二个数
[root@localhost ~]# [ $(ll /usr | wc -l) -le 15 ] && echo "目录太少"
目录太少
[root@localhost ~]# [ $(ll /usr | wc -l) -ge 10 ] && echo "目录太多"
目录太多
[root@localhost ~]# Free1=$(free -m | grep "Mem:" | awk ‘{print $6}’)
[root@localhost ~]# [ $Free1 -lt 1024 ] && echo ${Free1}MB
459MB
[root@localhost ~]# [ $Free1 -gt 300 ] && echo ${Free1}MB
459MB
①字符串比较通常用来检查用户输入、系统环境等是否满足条件,在提供交互式操作的Shell脚本中,也可用来判断用户输入的位置参数是否符合要求。
格式1:[ 字符串1 = 字符串2 ];[ 字符串1 != 字符串2 ]
格式2:[ -z 字符串 ]
②比较的常用操作选项如下。
-:第一个字符串与第二个字符串相同。
!=:第一个字符串与第二个字符串不相同,其中"!"符号表示取反。
-z:检查字符串是否为空(Zero),对于未定义或赋予空值的变量将视为空串。
[root@localhost ~]# echo $LANG
zh_CN.UTF-8
[root@localhost ~]# [ $LANG != "en.US" ] && echo "Not en.US"
Not en.US
[root@localhost ~]# read -p "是否覆盖现有文件(yes/no)?" ACK
是否覆盖现有文件(yes/no)?yes
[root@localhost ~]# [ $ACK = "yes" ] && echo "覆盖"
覆盖
①逻辑测试指的是判断两个或多个条件之间的依赖关系。当系统任务取决于多个不同的条件时,根据这些条件是否同时成立或者只要有其中一个成立等情况,需要有一个测试的过程。
格式1:[ 表达式1 ] 操作符 [ 表达式2 ] ...
格式2:命令1 操作符 命令2 ...
②常用的逻辑测试操作如下,使用时放在不同的测试语句或命令之间。
&&:逻辑与,表示"而且",只有当前后两个条件都成立时,整个测试命令的返回值―才为0(结果成立)。使用test命令测试时,“&&"可改为"-a"。
||:逻辑或,表示"或者",只要前后两个条件中有一个成立,整个测试命令的返回值即为0(结果成立)。使用test命令测试时,“||"可改为"-o"。
!:逻辑否,表示"不",只有当指定的条件不成立时,整个测试命令的返回值才为0(结果成立)。
测试etc是否是目录,以及是否有读的权限,如果两个都是就打开它
[root@localhost ~]# [ -d /etc ] && [ -r /etc ] && echo "You can open it"
You can open it
测试etc是否是目录或者home是否是目录,如果有一个成立,就ok
[root@localhost ~]# [ -d /etc ] || [ -d /home ] && echo "ok"
ok
在上述逻辑测试的操作选项中,"&&"和"||"通常也用于间隔不同的命令操作,其作用是相似的。实际上此前已经接触过"&&"操作的应用,如"make && make install"的编译安装操作。若要判断当前 Linux 系统的内核版本是否大于3.4,可以执行以下操作。其中,内核版本号通过 unane和awk 命令获得。
if语句的“分支”指的是不同测试结果所对应的执行语句(一条或多条)。对于单分支的选择结构,只有在“条件成立”时才会执行相应的代码,否则不执行任何操作。
if 条件测试操作
then
命令序列
fi
[root@localhost ~]# vim test1.sh
#!/bin/bash
if ls /opt > /dev/null
then
echo "it's ok"
fi
[root@localhost ~]# sh test1.sh
it's ok
[root@localhost ~]# vim test2.sh
#!/bin/bash
MOUNT_DIR="/mnt/centos7"
if [ ! -d $MOUNT_DIR ]
then
mkdir -p $MOUNT_DIR
echo "$MOUNT_DIR true"
fi
[root@localhost ~]# sh test2.sh
/mnt/centos7 true
[root@localhost ~]# vim test3.sh
#!/bin/bash
read -p "请输入文件名:" file
if [[ $file==*.sh ]]
then
echo "这是shel脚本"
fi
[root@localhost ~]# sh test3.sh
请输入文件名:test1.sh
这是shel脚本
对于双分支的选择结构,要求针对“条件成立”、“条件不成立”两种情况分别执行不同的操作。
if 条件测试操作
then
命令序列1
else
命令序列2
fi
[root@localhost ~]# vim test4.sh
#!/bin/bash
IP=192.168.32.1
ping -c 5 -i 0.5 -w 7 $IP &> /dev/null
if [ $? -eq 0 ]
then
echo "$IP is up"
else
echo "$IP is down"
fi
[root@localhost ~]# sh test4.sh
192.168.32.1 is up
[root@localhost ~]# vim test5.sh
#!/bin/bash
if [ $UID -eq 0 ]
then
echo "当前登录的用户是管理员root"
else
echo "当前登录的用户不是管理员root"
fi
[root@localhost ~]# sh test5.sh
当前登录的用户是管理员root
[root@localhost ~]# vim httpd1.sh
#!/bin/bash
set -x
pgrep aux | grep httpd | grep -v grep
if [ $? -ne 0 ]
then
if [ "$(rpm -q httpd)"=="未安装软件包 httpd" ]
then
yum install httpd -y
systemctl start httpd
echo "网站服务已安装启动"
else
systemctl start httpd
echo "网站服务已启动"
fi
else
echo "网站服务运行中"
fi
由于if语句可以根据测试结果的成立、不成立分别执行操作,所以能够嵌套使用,进行多次判断。
if 条件测试操作1
then
命令序列1
elif 条件测试操作2
then
命令序列2
else
命令序列2
fi
[root@localhost ~]# vim test6.sh
#!/bin/bash
read -p "请输入你的分数(0-100):" GRADE
if [[ $GRADE -le 100 && $GRADE -ge 85 ]]
then
echo "$GRADE 分:优秀!"
elif [[ $GRADE -le 84 && $GRADE -ge 60 ]]
then
echo "$GRADE 分:合格!"
elif [[ $GRADE -le 59 && $GRADE -ge 0 ]]
then
echo "$GRADE 分:不合格!"
else
echo "$GRADE :无效分数,请重新输入!"
fi
[root@localhost ~]# sh test6.sh
请输入你的分数(0-100):50
50 分:不合格!
[root@localhost ~]# sh test6.sh
请输入你的分数(0-100):70
70 分:合格!
[root@localhost ~]# sh test6.sh
请输入你的分数(0-100):90
90 分:优秀!
[root@localhost ~]# sh test6.sh
请输入你的分数(0-100):110
110 :无效分数,请重新输入!
[root@localhost ~]# vim fachao1.sh
#!/bin/bash
read -p "请输入你的考试分数(0-100):" GRADE
if [ $GRADE -eq 100 ]
then
echo "$GRADE 分:恭喜你获得满分的成绩!"
elif [[ $GRADE -le 99 && $GRADE -ge 90 ]]
then
echo "$GRADE 分:请你将错的题目罚抄20遍!"
elif [[ $GRADE -le 89 && $GRADE -ge 80 ]]
then
echo "$GRADE 分:请你将错的题目罚抄20遍!"
elif [[ $GRADE -le 79 && $GRADE -ge 60 ]]
then
echo "$GRADE 分:请你将错的题目罚抄30遍!"
elif [[ $GRADE -le 59 && $GRADE -ge 0 ]]
then
echo "$GRADE 分:请你将全部的题目罚抄30遍!"
else
echo "$GRADE :无效的考试分数,请你重新输入考试分数!"
fi
:wq
[root@localhost ~]# sh fachao1.sh
请输入你的考试分数(0-100):115
115 :无效的考试分数,请你重新输入考试分数!
[root@localhost ~]# sh fachao1.sh
请输入你的考试分数(0-100):100
100 分:恭喜你获得满分的成绩!
[root@localhost ~]# sh fachao1.sh
请输入你的考试分数(0-100):95
95 分:请你将错的题目罚抄20遍!
[root@localhost ~]# sh fachao1.sh
请输入你的考试分数(0-100):85
85 分:请你将错的题目罚抄20遍!
[root@localhost ~]# sh fachao1.sh
请输入你的考试分数(0-100):70
70 分:请你将错的题目罚抄30遍!
[root@localhost ~]# sh fachao1.sh
请输入你的考试分数(0-100):35
35 分:请你将全部的题目罚抄30遍!
case语句主要使用于以下情况:某个变量存在多种取值,需要对其中的每一种取值分别执行不同的命令序列。这种情况与多分支if语句非常相似,只不过if语句需要判断多个不同的条件,而case语句只是判断一个变量的不同取值。
case 变量值 in
模式1)
命令序列1
;;
模式2)
命令序列2
;;
......
*)
默认命令序列
esac
[root@localhost ~]# vim test7.sh
#!/bin/bash
case $1 in
start)
/usr/bin/systemctl $1 httpd
echo "正在开启httpd进程"
;;
stop)
/usr/bin/systemctl $1 httpd
echo "正在停止httpd进程"
;;
restart)
/usr/bin/systemctl $1 httpd
echo "正在重启httpd进程"
;;
status)
/usr/bin/systemctl $1 httpd > /dev/null
echo "正在查看httpd进程状态:active (running)"
;;
*)
echo "请输入有效的命令:start或stop或restart或status"
esac
[root@localhost ~]# sh test7.sh st
请输入有效的命令:start或stop或restart或status
[root@localhost ~]# sh test7.sh stop
正在停止httpd进程
[root@localhost ~]# sh test7.sh start
正在开启httpd进程
[root@localhost ~]# sh test7.sh restart
正在重启httpd进程
[root@localhost ~]# sh test7.sh status
正在查看httpd进程状态:active (running)
[root@localhost ~]# vim fachao2.sh
#!/bin/bash
read -p "请输入你的考试分数(0-100):" GRADE
case $GRADE in
100)
echo "$GRADE 分:恭喜你获得满分的成绩!"
;;
9[0-9])
echo "$GRADE 分:请你将错的题目罚抄10遍!"
;;
8[0-9])
echo "$GRADE 分:请你将错的题目罚抄20遍!"
;;
[6-7][0-9])
echo "$GRADE 分:请你将错的题目罚抄30遍!"
;;
[0-9]|[1-5][0-9])
echo "$GRADE 分:请你将全部的题目罚抄30遍!"
;;
*)
echo "$GRADE :无效的考试分数,请你重新输入考试分数!"
esac
:wq
[root@localhost ~]# sh fachao2.sh
请输入你的考试分数(0-100):115
115 :无效的考试分数,请你重新输入考试分数!
[root@localhost ~]# sh fachao2.sh
请输入你的考试分数(0-100):100
100 分:恭喜你获得满分的成绩!
[root@localhost ~]# sh fachao2.sh
请输入你的考试分数(0-100):95
95 分:请你将错的题目罚抄10遍!
[root@localhost ~]# sh fachao2.sh
请输入你的考试分数(0-100):85
85 分:请你将错的题目罚抄20遍!
[root@localhost ~]# sh fachao2.sh
请输入你的考试分数(0-100):65
65 分:请你将错的题目罚抄30遍!
[root@localhost ~]# sh fachao2.sh
请输入你的考试分数(0-100):45
45 分:请你将全部的题目罚抄30遍!
[root@localhost ~]# sh fachao2.sh
请输入你的考试分数(0-100):7
7 分:请你将全部的题目罚抄30遍!
1、使用[]或test命令可以执行条件测试操作,包括文件测试、整数测试、字符串测试以及逻辑测试。
2、执行命令或程序后会返回一个状态值,若返回值为0,表示执行成功;若不为0,则表示执行失败或出现异常。
3、通过使用if语句,可以根据条件有选择地执行不同操作,选择类型包括单分支、双分支、多分支。
4、case语句可根据变量的不同取值执行不同的命令序列,比多分支的if语句结构更加清晰。