1 if 分支语句
在 Shell 脚本应用中,if 语句是最为常用的一种流程控制方式,用来根据特定的条件测试结果,分别执行不同的操作。
根据不同的复杂程度,if 语句的选择结构可以分为三种基本类型,适用于不同的应用场合:
单分支 if 语句
双分支 if 语句
多分支 if 语句
1.1 单分支if语句
对于单分支的选择结构,只有在“条件成立”时才会执行相应的代码,否则不执行任何操作。
- 语法:
if 条件测试语句
then
命令序列
fi
条件测试语句既可以是“[条件表达式]”语句,也可以是其他可执行的命令语句。
命令序列指的是一条或多条可执行的命令行,也包括嵌套使用的 if 语句或其他流程控制语句。
- 单分支 if 语句的执行流程:
首先判断条件测试操作的结果,如果返回值为 0,表示条件成立,执行 then 后面的命令序列,一直到遇见 fi 结束判断为止,继续执行其他脚本代码。
如果返回值不为 0,则忽略 then 后面的命令序列,直接跳至 fi 行以后执行其他脚本代码。
- 示例1
#!/bin/bash
read -p "请输入一个数字:" num
if [ $num -gt 5 ]
then
echo "$num 大于 5"
fi
# 也可以写成
if [ $num -gt 5 ];then echo "$num 大于 5";fi
# 或者
[ $num -gt 5 ] && echo "$num 大于 5"
- 示例2
if [ "$USER" != "root" ]
then
echo "当前用户不是root用户,权限不足"
exit 3
fi
ls
exit命令表示退出脚本,不再执行其它代码
3表示退出后的返回状态值
1.2 双分支if语句
对于双分支的选择结构,要求针对“条件成立”“条件不成立”两种情况分别执行不同的操作。
- 语法
if 条件测试语句
then
命令序列1
else
命令序列2
fi
- 双分支 if 语句的执行流程
首先判断条件测试语句的结果,如果条件成立,则执行then后面的命令序列 1,忽略 else 及后面的命令序列 2,直到遇见 fi 结束判断。
如果条件不成立,则忽略 then 及后面的命令序列 1,直接跳至 else 后面的命令序列 2 并执行,直到遇见 fi 结束判断。
- 示例
#!/bin/bash
read -p "请输入一个数字num1:" num1
read -p "请输入一个数字num2:" num2
if [ $num1 -lt $num2 ]
then
echo "$num1 $num2"
else
echo "$num2 $num1"
fi
# 通过位置参数 $1 提供目标主机地址
ping $1 -c 4 -i 0.2 &>/dev/null
if [ $? -eq 0 ]
then
echo "$host连接成功"
else
echo "$host连接失败"
fi
-c 和 -i:分别表示发送测试包的个数和时间间隔
&>/dev/null:将ping执行过程中的输出信息丢弃
1.3 多分支if语句
- 语法
if 条件测试语句1
then
命令序列1
elif 条件测试语句2 # 可以有n个
then
命令序列2
else
命令序列2
fi
多分支 if 语句的执行流程:
首先判断条件测试语句 1 的结果,如果条件 1 成立,则执行命令序列 1,然后跳至 fi 结束判断。
如果条件 1 不成立,则继续判断条件测试语句 2 的结果,如果条件 2 成立,则执行命令序列 2,然后跳至 fi结束判断…
如果所有的条件都不满足,则执行 else 后面的命令序列n,直到遇见 fi 结束判断。
- 示例
#!/bin/bash
read -p "请输入成绩:" source
if [ $source -ge 0 ] && [ $source -lt 60 ]
then
echo "成绩不合格"
elif [ $source -ge 60 ] && [ $source -lt 75 ]
then
echo "成绩合格"
elif [ $source -ge 75 ] && [ $source -lt 90 ]
then
echo "成绩良好"
elif [ $source -ge 90 ] && [ $source -lt 100 ]
then
echo "成绩优秀"
elif [ $source -eq 100 ]
then
echo "满分"
else
echo "输入错误"
fi
2 case分支语句
针对变量额不同取值,分别执行不同的命令序列这种情况与多分支的if语句非常相似,只不过if语句需要判断多个不同的条件,而case语句只是判断一个变量的不同取值。
- 语法
case 变量值 in
模式1)
命令序列1
;;
模式2)
命令序列2
;;
......
*)
默认命令序列
;;
esac
变量值,即$变量名
*作为通配符,可匹配任意值
- case 语句的执行流程:
首先使用“变量值”与模式 1 进行比较,若取值相同则执行模式 1后的命令序列,直到遇见双分号“;;”后跳转至esac,表示结束分支。
若与模式 1 不相匹配,则继续与模式 2 进行比较,若取值相同则执行模式 2 后的命令序列,直到遇见双分号“;;”后跳转至 esac,表示结束分支……依此类推。
若找不到任何匹配的值,则执行默认模式“*)” 后的命令序列,直到遇见 esac 后结束分支。
- 注意
双分号“;;”表示命令序列的结束。
模式字符串中,可以用方括号表示一个连续的范围,如“[0-9]”;还可以用“|”表示或,如“A|B”。
- 示例
#!/bin/bash
read -p "请输入月份:" month
case $month in
1|3|5|[7-8]|10|12)
echo "$month月有31天"
;;
2)
read -p "请输入年份:" year
if [ $(echo $year%4|bc) -eq 0 ] && [ $(echo $year%100|bc) -ne 0 ] || [ $(echo $year%400|bc) -eq 0 ]
then
echo "$year年的$month月有29天"
else
echo "$year年的$month月有28天"
fi
;;
4|6|9|11)
echo "$month月有30天"
;;
*)
echo "月份输入错误"
esac