Shell编程—结构化命令
1使用if-then语句
f-then语句有如下格式。
if command then commands fi
bash shell的if语句会运行if后面的那个命令。如果该命令的退出状态码是0(该命令成功运行),位于then部分的命令就会被执行。如果该命令的退出状态码是其他值, then部分的命令就不会被执行,bash shell会继续执行脚本中的下一个命令。fi语句用来表示if-then 语句到此结束。
举例:
$ vim test1.sh #!/bin/bash # testing the if statement if pwd then echo "It worked" fi
命令行运行该脚本时,会得到如下结果:
此外,还有一种写法:
if command; then commands fi
通过把分号放在待求值的命令尾部,就可以将then语句放在同一行上了。
2 if-then-else语句
格式:
if command then commands else commands fi
3 嵌套if
有时需要检查脚本代码中的多种条件。对此,可以使用嵌套的if-then语句。
比如要检查/etc/passwd文件中是否存在某个用户名以及该用户的目录是否尚在,可以使用嵌套的if-then语句。嵌套的if-then语句位于主if-then-else语句的else代码块中。
$ ls -d /home/NoSuchUser/ /home/NoSuchUser/ $ $ vim test5.sh #!/bin/bash # Testing nested ifs testuser=NoSuchUser if grep $testuser /etc/passwd then echo "The user $testuser exists on this system." else echo "The user $testuser does not exist on this system." if ls -d /home/$testuser/ then echo "However, $testuser has a directory." fi fi
4 test命令
test命令提供了在if-then语句中测试不同条件的途径。如果test命令中列出的条件成立, test命令就会退出并返回退出状态码0。如果条件不成立,test命令就会退出并返回非零的退出状态码,使得if-then语句不会再被执行。
test命令的格式非常简单:
test condition
当用在if-then语句中时,test命令看起来是这样的:
if test condition then commands fi
如果不写test命令的condition部分,它会以非零的退出状态码退出,并执行else语句块:
$ vim test6.sh #!/bin/bash # Testing the test command if test then echo "No expression returns a True" else echo "No expression returns a False" fi
执行结果:
4.1数值比较
比 较 |
描 述 |
n1 -eq n2 |
检查n1是否与n2相等 |
n1 -ge n2 |
检查n1是否大于或等于n2 |
n1 -gt n2 |
检查n1是否大于n2 |
n1 -le n2 |
检查n1是否小于或等于n2 |
n1 -lt n2 |
检查n1是否小于n2 |
n1 -ne n2 |
检查n1是否不等于n2 |
举例:
$ vim numeric_test.sh #!/bin/bash # Using numeric test evaluations value1=10 value2=11 if [ $value1 -gt 5 ] then echo "The test value $value1 is greater than 5" fi if [ $value1 -eq $value2 ] then echo "The values are equal" else echo "The values are different" fi
第一个条件测试:
if [ $value1 -gt 5 ] : 测试变量value1的值是否大于5。
第二个条件测试:
if [ $value1 -eq $value2 ] : 测试变量value1的值是否和变量value2的值相等
结果:
4.2字符串比较
比 较 |
描 述 |
str1 = str2 |
检查str1是否和str2相同,会将所有的标点和大小写情况都考虑在内 |
str1 != str2 |
检查str1是否和str2不同,会将所有的标点和大小写情况都考虑在内 |
str1 < str2 |
检查str1是否比str2小 |
str1 > str2 |
检查str1是否比str2大 |
-n str1 |
检查str1的长度是否非0 |
-z str1 |
检查str1的长度是否为0 |
关于字符串顺序 :
当要开始使用测试条件的大于或小于功能时,就会出现两个问题:
- 大于号和小于号必须转义,否则shell会把它们当作重定向符号,把字符串值当作文件名;
- 大于和小于顺序和sort命令所采用的不同。
4.3文件比较
比 较 |
描 述 |
-d file |
检查file是否存在并是一个目录 |
-e file |
检查file是否存在 |
-f file |
检查file是否存在并是一个文件 |
-r file |
检查file是否存在并可读 |
-s file |
检查file是否存在并非空 |
-w file |
检查file是否存在并可写 |
-x file |
检查file是否存在并可执行 |
-O file |
检查file是否存在并属当前用户所有 |
-G file |
检查file是否存在并且默认组与当前用户相同,只比较默认组,不会比较其他组 |
file1 -nt file2 |
检查file1是否比file2新 |
file1 -ot file2 |
检查file1是否比file2旧 |
5复合条件测试
if-then语句允许你使用布尔逻辑来组合测试。有两种布尔运算符可用:
- [ condition1 ] && [ condition2 ] :要让then部分的命令执行,两个条件都必须满足。
- [ condition1 ] || [ condition2 ] :如果任意条件为TRUE,then部分的命令就会执行。
下例展示了AND布尔运算符的使用。
$ vim test22.sh #!/bin/bash if [ -d $HOME ] && [ -w $HOME/testing ] then echo "The file exists and you can write to it" else echo "I cannot write to the file" fi 结果: $ ./test22.sh I cannot write to the file $ $ touch $HOME/testing $ $ ./test22.sh The file exists and you can write to it
6 if-then的高级特性
6.1使用双括号
双括号命令允许你在比较过程中使用高级数学表达式,见下表:
符 号 |
描 述 |
val++ |
后增 |
val-- |
后减 |
++val |
先增 |
--val |
先减 |
! |
逻辑求反 |
~ |
位求反 |
** |
幂运算 |
<< |
左位移 |
>> |
右位移 |
& |
位布尔和 |
| |
位布尔或 |
&& |
逻辑和 |
|| |
逻辑或 |
6.2使用双方括号
双方括号命令提供了针对字符串比较的高级特性。双方括号命令的格式如下:
[[ expression ]]
它提供了test命令未提供的另一个特性——模式匹配(就是支持正则表达式)。
7case命令
格式:
case variable in pattern1 | pattern2) commands1;; pattern3) commands2;; *) default commands;; esac