Shell编程 - 判断篇
1. 字符串比较符
运算符 | 描述 | 示例 |
---|---|---|
= | 等于 | [ "a" = "a" ]为true |
!= | 不等于 | [ "a" != "a" ]为false |
> | 大于,判断字符串时根据ASCII码表顺序,不常用 | 在[]表达式中:[ 2 > 1 ]为true 在[[]]表达式中:[[ 2 > 1 ]]为true 在(())表达式中:(( 3 > 2 ))为true |
< | 小于,判断字符串时根据ASCII码表顺序,不常用 | 在[]表达式中:[ 2 < 1 ]为false 在[[]]表达式中:[[ 2 < 1 ]]为false 在(())表达式中:(( 3 < 2 ))为false |
>= | 大于等于 | 在(())表达式中:(( 3 >= 2 ))为true |
<= | 小于等于 | 在(())表达式中:(( 3 <= 2 ))为false |
-n | 字符串长度不等于0为真 | VAR1=1;VAR2="" [ -n "$VAR1" ]为true [ -n "$VAR2" ]为false |
-z ⭐ | 字符串长度等于0为真 | VAR1=1;VAR2="" [ -z "$VAR1" ]为false [ -z "$VAR2" ]为true |
str | 字符串存在为真 | VAR1=1;VAR2="" [ $VAR1 ]为true [ $VAR2 ]为false |
条件表达式-字符串对比 | 说明 |
---|---|
"str1" = "str2" | str1 是否等于str2,如果相等则为真 |
"str1" != "str2" | str1 是否等于str2,如果不相等则为真 |
-z "str" | zero 检查str字符串是否为空,空的则为真。 |
-n "str" | not zero 检查str字符串是否为空,非空的则为真。 |
需要注意的是,使用-z或-n判断字符串长度时,变量要加双引号。⭐
# 加了双引号才能正常判断是否为空
# [ -z "$a" ] && echo yes || echo no
yes
# [ -n "$a" ] && echo yes || echo no
no
# 使用了双中括号就不用了双引号
# [[ -n $a ]] && echo yes || echo no
no
# [[ -z $a ]] && echo yes || echo no
yes
- 对比2个字符串是否相等
input=start
[ "$input" = "start" ] && echo "成立 " || echo "失败"
成立
str1=hello996
str2=hello007
[ "$str1" = "$str2" ] && echo "成立 " || echo "失败"
失败
在进行字符串比较的时候变量尾巴可以加上个x,防止变量为空,造成匹配/执行失败.
案例1. 检查selinux是否关闭脚本,如果没有关闭提示是否要关闭,yes则关闭,其他就不关闭⭐⭐
- 初级
- 进阶
- selinux
案例2. 给使用read指令的脚本增加判断功能,如果变量为空则退出⭐
read -p "请输入数字num1 num2:" num1 num2
if [ -z "$num1" ];then
echo error
exit 1
fi
if [ -z "$num2" ];then
echo error
exit 1
fi
2. 文件测试
测试符 | 描述 | 示例 |
---|---|---|
-e | 文件或目录存在为真 | [ -e path ] path存在为true |
-f | 文件存在为真 | [ -f file_path ] 文件存在为true |
-d | 目录存在为真 | [ -d dir_path ] 目录存在为true |
-r | 有读权限为真 | [ -r file_path ] file_path有读权限为true |
-w | 有写权限为真 | [ -w file_path ] file_path有写权限为true |
-x | 有执行权限为真 | [ -x file_path ] file_path有执行权限为true |
-s | 文件存在并且大小大于0为真 | [ -s file_path ] file_path存在并且大小大于0为true |
-
- 条件测试语句,不会直接提示对错,通过返回值提示.
[ -f /etc/hosts ] echo $?
-
- 判断文件是否存在格式
[ -f /etc/hosts ] && echo "成立 " || echo "失败" [ -f /etchosts ] && echo "成立 " || echo "失败" test -f /etchosts && echo "成立 " || echo "失败"
注意格式:[空格 -f /etc/hosts 空格]
检查目录是否存在
案例3. 检查指定的文件(目录,软链接)脚本,如果文件存在则显示文件名字,大小,权限,硬链接数,所属用户和用户组,文件修改时间。如果文件不存在则输出文件不存在。⭐⭐⭐
#1.vars
thing=$1
#2.判断参数
if [ $# -eq 0 ];then
echo "HELP:$0 + 参数"
exit
fi
#3.判断
#目录
if [ -d $thing ];then
echo "$thing is a dir"
echo "目录大小:`du -sh $thing|awk '{print $1}'`"
echo "目录权限:`ls -ld $thing|awk '{print $1}'|sed -r 's#^.##g'`/`stat $thing|awk -F '[(/]' 'NR==4{print $2}'`"
echo "硬链接数:`ls -ld $thing|awk '{print $2}'`"
echo "所属用户:`ls -ld $thing|awk '{print $3}'`"
echo "所属用户组:`ls -ld $thing|awk '{print $4}'`"
echo "修改时间:`ls -ld $thing|awk '{print $6,$7,$8}'`"
exit
fi
#软链接
[ -L $thing ] && {
echo $thing is a soft_link
echo "文件大小:`ls -l $thing|awk '{print $5}'`"
echo "权限:`ls -l $thing|awk '{print $1}'|sed -r 's#^.##g'`/`stat $thing|awk -F '[(
/]' 'NR==4{print $2}'`"
echo "硬链接数:`ls -l $thing|awk '{print $2}'`"
echo "所属用户:`ls -l $thing|awk '{print $3}'`"
echo "所属用户组:`ls -l $thing|awk '{print $4}'`"
echo "修改时间:`ls -l $thing|awk '{print $6,$7,$8}'`"
exit 0
}
#文件
if [ -f $thing ];then
echo "$thing is a file"
if [ -x $thing ];then
echo "该文件有执行权限"
else
echo "该文件没有执行权限"
fi
echo "文件大小:`ls -l $thing|awk '{print $5}'`"
echo "权限:`ls -l $thing|awk '{print $1}'|sed -r 's#^.##g'`/`stat $thing|awk -F '[(
/]' 'NR==4{print $2}'`"
echo "硬链接数:`ls -l $thing|awk '{print $2}'`"
echo "所属用户:`ls -l $thing|awk '{print $3}'`"
echo "所属用户组:`ls -l $thing|awk '{print $4}'`"
echo "修改时间:`ls -l $thing|awk '{print $6,$7,$8}'`"
else
echo "$thing dose not exist"
fi
3. 布尔运算符
运算符 | 描述 | 示例 |
---|---|---|
! | 非关系,条件结果取反 | [ ! 1 -eq 2 ]为true |
-a | 和关系,在[]表达式中使用 | [ 1 -eq 1 -a 2 -eq 2 ]为true |
-o | 或关系,在[]表达式中使用 | [ 1 -eq 1 -o 2 -eq 1 ]为true |
4. 逻辑判断符
判断符 | 描述 | 示例 |
---|---|---|
&& | 逻辑和,在[[]]和(())表达式中或判断表达式是否为真时使用 | [[ 1 -eq 1 && 2 -eq 2 ]]为true (( 1 == 1 && 2 == 2 ))为true [ 1 -eq 1 ] && echo yes 如果&&前面表达式为true则执行后面的 |
|| | 逻辑或,在[[]]和(())表达式中或判断表达式是否为真时使用 | [[ 1 -eq 1 || 2 -eq 1 ]]为true (( 1 == 1 || 2 == 2 ))为true [ 1 -eq 2 ] || echo yes 如果||前面表达式为false则执行后面的 |
5. 使用正则判断
=~ is match(支持正则)
num=666
[[ $num =~ [0-9] ]] && echo "成立 " || echo "失败"
成立
num=hello999
[[ $num =~ [0-9] ]] && echo "成立 " || echo "失败"
案例4. 书写一个脚本通过read读取输入,判断输入是整数,浮点数(小数),还是字符⭐
整数正则: ^-?[0-9]+$
浮点数: ^-?[0-9]+.[0-9]+$ 1.0 2.0 3.0 4.5
字符串: ^[a-zA-Z0-9]+$ aa33 33aa bb77
6. if语句
- 单分支
->格式:
if 条件;then
满足条件后执行的内容。
fi
if 条件
then
满足条件后执行的内容。
fi
->案例:
[ $# -eq 2 ] || {
echo "必须要2个数字"
exit 1
}
if [ $# -ne 2 ];then
echo "脚本必须要2个参数"
exit 1
- 双分支
格式:
if 条件;then
满足条件后执行的内容。
else
不满足条件执行的内容。
fi
案例5. 书写服务检查脚本,执行的时候输入服务名字检查是否运
行,检查是否开启自启动.⭐
- 多分支
格式:
#第1次判断
if 条件;then
满足条件后执行的内容。
#第2次判断
elif 条件;then
#else if
满足elif条件,执行的内容。
#第3次判断 还可以继续增加.
elif 条件;then
满足elif条件,执行的内容。
else
不满足条件执行的内容。
fi
案例6. 多分支格式比较大小脚本⭐
案例7. 检查磁盘分区的情况⭐
6. case语句
-
概述
相当于是if中的字符串对比判断. (= ) .比大小,文件,目录判断,正则只能使用if.
类似于条件分支语句,case一般用于实现有多种选择的脚本(菜单 选择)。
这个功能:if或多分支if实现,如果使用case语句会更加清晰直观. -
格式
case "变量" in
1)
命令
2)
命令
*)
命令(保底的默认输出)
esac
案例8. 判断系统发行版本⭐
判断当前系统是kylin,ubuntu,centos,debian,xxxxx
系统是kylin或centos则输出红帽类系统,使用yum,rpm指令.
系统是debian或ubuntu则输出debian类系统,使用apt,dpkg指令.
核心问题:如何知晓当前系统发行版本和版本号
1. hostnamectl的Operating System:行的第3列 获取系统发行版
本,但是版本号有问题.
2. 读取/etc/os-release文件 读取ID,VERSION_ID2个内容
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· winform 绘制太阳,地球,月球 运作规律
· AI与.NET技术实操系列(五):向量存储与相似性搜索在 .NET 中的实现
· 超详细:普通电脑也行Windows部署deepseek R1训练数据并当服务器共享给他人
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理
· 上周热点回顾(3.3-3.9)