结构化命令

news/2024/11/15 3:29:44/

章节目录:

    • 一、使用 if-then 语句
    • 二、if-then-else 语句
    • 三、嵌套 if 语句
    • 四、test 命令
      • 4.1 数值比较
      • 4.2 字符串比较
      • 4.3 文件比较
    • 五、复合条件测试
    • 六、if-then 的高级特性
      • 6.1 使用单括号
      • 6.2 使用双括号
      • 6.3 使用双方括号
    • 七、case 命令
    • 八、结束语

本章内容:

  • 使用 if-then 语句
  • 嵌套 if 语句
  • test 命令
  • 复合条件测试
  • 使用双方括号和双括号
  • case 命令

一、使用 if-then 语句

有一类命令允许脚本根据条件跳过部分命令,改变执行流程。这样的命令通常被称为结构化命令structured command )。其中最基本的结构化命令是 if-then 语句。

  • 语句格式如下
if command
thencommands
fi
  • bash shell 的 if 语句会运行 if 之后的命令。

  • 如果该命令的退出状态码为 0 (命令成功运行),那么位于 then 部分的命令就会被执行

  • 如果退出状态码是其他值,则 then 部分的命令不会被执行,bash shell 会接着处理脚本中的下一条命令

  • fi 语句用来表示 if-then 语句到此结束

  • 应用示例

# 1.脚本内容。(这里第一个if块使用了存在的命令;第二个if块使用不存在的命令。)
[root@VM-8-11-centos testdir]# cat test.sh 
#!/bin/bash
if whoami
thenecho "ok"
fiecho -e "\n============\n"if notCommand
thenecho "ok"
fi# 2.执行脚本。(第一个if块顺利执行then;第二个if块未执行then。)
[root@VM-8-11-centos testdir]# ./test.sh 
root
ok============./test.sh: line 9: notCommand: command not found

二、if-then-else 语句

当 if 语句中的命令返回非 0 退出状态码时,bash shell 会执行 else 部分中的命令。

  • 语句格式如下
if command
thencommands
elsecommands
fi
  • 应用示例
# 1.脚本内容。(if块使用不存在的命令。)
[root@VM-8-11-centos testdir]# cat ./test.sh 
#!/bin/bash
if notCommand
thenecho "ok"
elseecho "use the correct command!"
fi# 2.执行脚本。(if退出码非0,执行else块。)
[root@VM-8-11-centos testdir]# ./test.sh 
./test.sh: line 2: notCommand: command not found
use the correct command!
  • 跟 then 部分一样,else 部分可以包含多条命令
  • fi 语句说明 else 部分结束

三、嵌套 if 语句

有时需要在脚本中检查多种条件。对此,可以使用嵌套的 if-then 语句。

  • 语句格式如下
if command1
thencommands
elif command2
thencommands
elsecommands
fi
  • elif 语句提供了另一个要测试的命令,这类似于原始的 if 语句行
  • 每个代码块会根据命令是否返回退出状态码 0 来执行。
  • 记住,bash shell 会依次执行 if 语句,只有第一个返回退出状态码 0 的语句中的 then 部分会被执行
  • 应用示例
# 1.脚本内容。(if不成立,elif都成立。 -> 提示:依次执行,只有第一个退出状态码0的then语句才会被执行。)
[root@VM-8-11-centos testdir]# cat test.sh 
#!/bin/bash
if notCommand
thenecho "if block"
elif whoami
thenecho "elif1 block"
elif pwd
thenecho "elif2 block"
elseecho "else block"
fi# 2.执行脚本。(只有第一个elif的then被执行到了。 -> 提示:如果if和elif退出状态码都非0,才会执行else)
[root@VM-8-11-centos testdir]# ./test.sh 
./test.sh: line 2: notCommand: command not found
root
elif1 block

四、test 命令

test 命令可以在 if-then 语句中测试不同的条件。如果 test 命令中列出的条件成立,那么就会退出并返回退出状态码 0

  • 当用在 if-then 语句中时,格式如下
if test condition
thencommands
elsecommands
fi
  • 如果不写 test 命令的 condition 部分,则它会以非 0 的退出状态码退出并执行 else 代码块语句。
  • 如果加入了条件,则 test 命令会测试该条件。
  • bash shell 提供了另一种条件测试方法,无须在 if-then 语句中写明 test 命令:
if [ condition ]
thencommands
fi
  • 方括号定义了测试条件。
  • 注意事项:第一个方括号之后和第二个方括号之前必须留有空格,否则就会报错。

4.1 数值比较

使用 test 命令最常见的情形是对两个数值进行比较。

  • test 命令的数值比较功能
比较描述
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
  • 应用示例
# 1.脚本内容。(定义两个整数值进行测试比较。)
[root@VM-8-11-centos testdir]# cat test.sh 
#!/bin/bash
num1=10
num2=11
#
if [ $num1 -gt 5 ]
thenecho "$num1 is greater than 5."
fi
#
if [ $num1 -eq $num2 ]
thenecho "The values are equal."
elseecho "The values are different."
fi# 2.执行脚本。
[root@VM-8-11-centos testdir]# ./test.sh 
10 is greater than 5.
The values are different.
  • 注意事项对于测试条件,bash shell 只能处理整数。尽管可以将浮点值用于某些命令( 比如 echo ),但它们在条件测试下无法正常工作。

4.2 字符串比较

测试条件还允许比较字符串值

  • test 命令的字符串比较功能
比较描述
str1 = str2检查 str1 是否和 str2 相同。
str1 != str2检查 str1 是否和 str2 不同。
str1 < str2检查 str1 是否小于 str2 。
str1 > str2检查 str1 是否大于 str2。
-n str1检查 str1 的长度是否不为 0。
-z str1检查 str1 的长度是否为 0。

4.2.1 字符串相等性

字符串的相等或不等条件不言自明。

  • 应用示例
# 1.脚本内容。(比较两个字符串是否相同。)
[root@VM-8-11-centos testdir]# cat test.sh 
#!/bin/bash
str1="hello"
#
if [ "hello" = $str1 ]
thenecho "euqal."
elseecho "not equal."
fi# 2.执行脚本。
[root@VM-8-11-centos testdir]# ./test.sh 
euqal.
  • 注意事项:在比较字符串的相等性时,比较测试会将所有的标点大小写情况都考虑在内。

4.2.2 字符串顺序

要测试一个字符串是否大于或小于另一个字符串就开始变得棘手了。

  • 使用测试条件的大于或小于功能时,会出现两个经常困扰的问题
    • 大于号小于号必须转义否则 shell 会将其视为重定向符,将字符串值当作文件名。
    • 大于和小于顺序于 sort 命令所采用的不同
  • 问题一
# 1.脚本内容。(比较时,没有对大于号进行转义。)
[root@VM-8-11-centos testdir]# cat test.sh
#!/bin/bash
str1=soccer
str2=zorbfootball
#
if [ $str1 > $str2 ]
thenecho "$str1 is greater than $str2 ."
elseecho "$str1 is less than $str2 ."
fi# 2.执行脚本。(比较结果不符合预期,并且把大于号当作了重定向符号生成了新文件。)
[root@VM-8-11-centos testdir]# ./test.sh 
soccer is greater than zorbfootball .
[root@VM-8-11-centos testdir]# ls z*
zorbfootball
  • 问题一 - 正确使用示例
# 1.移除文件。
[root@VM-8-11-centos testdir]# rm -rf zorbfootball # 2.修改脚本内容。(添加转义。)
[root@VM-8-11-centos testdir]# vim test.sh 
[root@VM-8-11-centos testdir]# cat test.sh 
#!/bin/bash
str1=soccer
str2=zorbfootball
#
if [ $str1 \> $str2 ]
thenecho "$str1 is greater than $str2 ."
elseecho "$str1 is less than $str2 ."
fi# 3.执行脚本。(比较结果符合预期。)
[root@VM-8-11-centos testdir]# ./test.sh 
soccer is less than zorbfootball .# 4.是否又重定向生成了新的文件。
[root@VM-8-11-centos testdir]# ls z*
ls: cannot access z*: No such file or directory
  • 问题二
# 1.sort排序时,优先出现小写字母。
[root@VM-8-11-centos testdir]# cat 1.txt 
Soccer
soccer
[root@VM-8-11-centos testdir]# sort 1.txt 
soccer
Soccer
[root@VM-8-11-centos testdir]# vim test.sh 
[root@VM-8-11-centos testdir]# cat test.sh 
#!/bin/bash
str1=Soccer
str2=soccer
#
if [ $str1 \> $str2 ]
thenecho "$str1 is greater than $str2 ."
elseecho "$str1 is less than $str2 ."
fi# 2.执行脚本。(在比较测试中,大写字母被认为是小于小写字母的。)
[root@VM-8-11-centos testdir]# ./test.sh 
Soccer is less than soccer .
  • 比较测试中使用的是标准的 Unicode 顺序,根据每个字符的 Unicode 编码值来决定排序结果。
  • sort 命令使用的是系统的语言环境设置中定义的排序顺序。对于英语,语言环境设置指定了在排序顺序中小写字母出现在大写字母之前
  • 注意事项test 命令和测试表达式使用标准的数学比较符号来表示字符串比较。而用文本代码来表示数值比较

4.2.3 字符串大小

-n 和 -z 可以很方便地用于检查一个变量是否为空。

  • 应用示例
# 1.脚本内容。
[root@VM-8-11-centos testdir]# cat test.sh 
#!/bin/bash
str1=""
#
if [ -z "$str1" ]
thenecho "$str1 is empty."
elseecho "$str1 is not empty."
fi
#
if [ -n "$str1" ]
thenecho "$str1 is not empty."
elseecho "$str1 is empty."
fi# 2.执行脚本。
[root@VM-8-11-centos testdir]# ./test.sh is empty.is empty.
  • 注意事项空变量未初始化的变量会对 shell 脚本测试造成灾难性的影响如果不确定变量的内容,那么最好在将其用于数值或字符串比较之前先通过 -n 或 -z 来测试以下变量是否为空
  • 个人踩坑备注(-n 判断空字符串时,未加双引号引用变量,导致结果不符合预期。):
在shell中,引用变量时,加不加双引号是有区别的:1.如果不加双引号,shell会将变量展开为其值,并将其作为一个单词处理。这意味着,如果变量的值包含空格或其他特殊字符,这些字符会被解释为单词分隔符或特殊字符,可能会导致意外的结果。例如,假设有一个变量`var="hello world"`,如果不加双引号,使用`echo $var`命令输出的结果将是两个单词`hello``world`,而不是一个单词`hello world`2.如果加上双引号,shell会将变量展开为其值,并将其作为一个整体处理。这意味着,变量的值中的空格和其他特殊字符会被保留,不会被解释为单词分隔符或特殊字符。例如,使用`echo "$var"`命令输出的结果将是一个单词`hello world`,而不是两个单词`hello``world`。结论:因此,为了避免意外的结果,建议在引用变量时加上双引号。

4.3 文件比较

最后一类比较测试很有可能是 shell 编程中最为强大且用得最多得比较形式。它允许试 Linux 文件系统中文件和目录的状态

  • test 命令的文本比较功能
比较描述
-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 旧。
  • 应用示例
# 1.脚本内容。(需求:如果目标文件为空则进行删除。)
[root@VM-8-11-centos testdir]# cat test.sh 
#!/bin/bash
# Check if a file is empty.
fileName=/home/tmp/1.txt
#
echo
echo "checking if $fileName file is empty... "
# if exists
if [ -f $fileName ]
then# is empty.if [ -s $fileName ]thenecho "$fileName file exists and has data in it."echo "will not remove this file."elseecho "$fileName file exists, but is empty."echo "deleting this file..."rm -rf $fileNameecho "$fileName file, successfully deleted!"fi#
elseecho "The $fileName file does not exist."
fi# 2.被操作文件为非空文件。
[root@VM-8-11-centos testdir]# ls -sh /home/tmp/1.txt
4.0K /home/tmp/1.txt# 3.执行脚本。
[root@VM-8-11-centos testdir]# ./test.sh checking if /home/tmp/1.txt file is empty... 
/home/tmp/1.txt file exists and has data in it.
will not remove this file.

五、复合条件测试

if-then 语句允许使用布尔逻辑将测试条件组合起来。

  • 布尔运算符 AND 来组合两个条件(都必须满足):[ condition ] && [ condition ]

  • 布尔运算符 OR 来组合两个条件(任意条件满足):[ condition ] || [ condition ]

  • 应用示例

# 1.脚本内容。(如果$HOME目录存在且该目录下有名为newfile的可写文件,则提示写入。)
[root@VM-8-11-centos testdir]# cat test.sh 
#!/bin/bash
if [ -d $HOME ] && [ -w $HOME/newfile ]
thenecho "the file exists and you can write to it."
elseecho "you cannot write to the file."
fi# 2.当前无此文件。
[root@VM-8-11-centos testdir]# ls -l $HOME/newfile
ls: cannot access /root/newfile: No such file or directory
[root@VM-8-11-centos testdir]# ./test.sh 
you cannot write to the file.# 3.创建文件,再次执行脚本测试。
[root@VM-8-11-centos testdir]# touch $HOME/newfile
[root@VM-8-11-centos testdir]# ls -l $HOME/newfile
-rw-r--r-- 1 root root 0 Jun 11 10:32 /root/newfile
[root@VM-8-11-centos testdir]# ./test.sh 
the file exists and you can write to it.# 4.清理操作。
[root@VM-8-11-centos testdir]# rm -rf $HOME/newfile

六、if-then 的高级特性

bash shell 还提供了 3 个可在 if-then 语句中使用的高级特性

  • shell 中执行命令单括号
  • 用于数学表达式双括号
  • 用于高级字符串处理功能的双方括号

6.1 使用单括号

单括号允许if 语句中使用子 shell

  • 在 bash shell 执行命令之前,会先创建一个子 shell ,然后在其中执行命令。

  • 如果命令成功结束,则退出状态码会被设为 0 ,then 部分就会被执行。否则,不执行 then 部分的命令。

  • 应用示例

# 1.脚本内容。(使用子shell进行测试。)
[root@VM-8-11-centos testdir]# cat test.sh 
#!/bin/bash
echo $BAHS_SUBSHELL
#
if (echo $BASH_SUBSHELL)
thenecho "successsfully."
elseecho "not successfully."
fi# 2.执行脚本。(1表示使用了子shell。)
[root@VM-8-11-centos testdir]# ./test.sh 1
successsfully.

6.2 使用双括号

双括号命令允许在比较过程中使用高级数学表达式。相较于 test 命令进行比较时,双括号命令提供了更多的数学符号

  • 除了 test 命令使用的标准数学运算符,还有
符号描述
val ++后增。
val后减。
++ val先增。
val先减。
!逻辑求反。
~位求反。
**幂运算。
<<左位移。
>>右位移。
&位布尔 AND。
|位布尔 OR。
&&逻辑 AND。
||逻辑 OR。
  • 双括号命令既可以在 if 语句中使用,也可以在脚本中的普通命令里用来赋值。
  • 应用示例
# 1.脚本内容。(num1的平方是否大于90,并将该值的平方赋值给num2)
[root@VM-8-11-centos testdir]# cat test.sh 
#!/bin/bash
num1=10
#
if (( $num1 ** 2 > 90 ))
then(( num2=$num1 ** 2))echo "the suqare of $num1 is $num2."echo "which is greater than 90."
fi# 2.执行脚本。
[root@VM-8-11-centos testdir]# ./test.sh 
the suqare of 10 is 100.
which is greater than 90.
  • 注意事项:双括号中表达式的大于号不用转义。这是双括号命令的又一个优越性的体现。

6.3 使用双方括号

双方括号命令提供了针对字符串比较的高级特性

  • 除了 test 命令使用的标准字符串比较,还提供了 test 命令所不具备的另一个特性——模式匹配
  • 在进行模式匹配时,可以定义通配符正则表达式来匹配字符串。
  • 应用示例
# 1.脚本内容。(通配符匹配)
[root@VM-8-11-centos testdir]# cat test.sh 
#!/bin/bash
#
echo $BASH_VERSION
#
if [[ $BASH_VERSION == 4.* ]]
thenecho "using version 4 series."
fi# 2.执行脚本。
[root@VM-8-11-centos testdir]# ./test.sh 
4.2.46(2)-release
using version 4 series.
  • 注意事项:双方括号在 bash shell 中运行良好。不过要小心,不是所有的 shell 都支持双方括号

七、case 命令

尝试计算一个变量的值,在一组可能的值中寻找特定值。case 命令会采用列表格式检查变量的多个值,就无须再写大量的 elif 语句来检查同一个变量的值了。

  • 语句格式如下
casein
模式1)command1command2...commandN;;
模式2)command1command2...commandN;;
esac
  • case 命令会将指定变量与不同模式进行比较。如果变量与模式匹配,那么 shell 就会执行为该模式指定的命令
  • 可以通过竖线运算符在一行中分隔出多个模式
  • 星号会捕获所有与已知模式不匹配的值。
  • 应用示例
# 1.脚本内容。(判断当前用户类型。)
[root@VM-8-11-centos testdir]# cat test.sh 
#!/bin/bash
case $USER in
"jan" | "lucy")echo "$USER is a ordinary user.";;
"root")echo "$USER is the administrator.";;
*)echo "$USER It's a different type of account."
esac#  2.执行脚本。
[root@VM-8-11-centos testdir]# ./test.sh 
root is the administrator.

八、结束语


“-------怕什么真理无穷,进一寸有一寸的欢喜。”

微信公众号搜索:饺子泡牛奶


http://www.ppmy.cn/news/327204.html

相关文章

华为OD机试真题 JavaScript 实现【最长的连续子序列】【2022Q4 100分】

一、题目描述 有N个正整数组成的一个序列&#xff0c;给定一个整数sum&#xff0c;求长度最长的的连续子序列使他们的和等于sum&#xff0c;返回该子序列的长度&#xff0c;如果没有满足要求的序列返回-1。 二、输入描述 第1行有N个正整数组成的一个序列。 第2行给定一个整…

苹果X更换电池-苹果x电池寿命80%要换吗?

手机电池寿命小于80%&#xff0c;是否需要更换电池&#xff0c;这主要取决于用户的使用体验。苹果电池更换。 我爱家电维修网告诉你如果感觉还可以&#xff0c;没有明显的使用经验&#xff0c;不一定需要立即更换&#xff0c;可以继续使用。 如果感觉寿命明显下降&#xff0c;…

苹果x面容id不可用是什么原因_iPhone X显示面容ID不可用,大神一招FaceID恢复

iPhone X显示面容ID不可用&#xff0c;大神一招Face ID恢复正常&#xff0c;解锁无忧 Face ID(面容ID)是iPhone X的安全解锁功能&#xff0c;也是iPhone X的最大亮点&#xff0c;只需要一眼就可以安全地解锁。但iPhone X面容ID不可用是实际维修中最常见的故障&#xff0c;也是这…

苹果x面容id不可用是什么原因_iPhone X使用体验!苹果手机那么保值是有原因的...

在竞争如此激烈的手机市场之下&#xff0c;苹果所要面临的压力同样巨大。在2018年第二季度的出货量报告中便可得知&#xff0c;华为已经赶超苹果&#xff0c;跃居全球第二。在众多国产手机品牌快速崛起的环境之下&#xff0c;苹果的销量更加难以稳定。不得不承认的是&#xff0…

苹果x与苹果xs的区别_这四款X系列的苹果手机怎么选择呢

X系列有4款经典机型XR&#xff0c;XS&#xff0c;X&#xff0c;XSMax 那么这四款应该怎么选呢&#xff1f; 首先&#xff0c;屏幕尺寸方面大家可以先了解下&#xff1a; 这里我以在四者中&#xff0c;价格和配置属于中间的Xs来做对比&#xff0c;能够更加清晰得对比出四款机型的…

苹果x和xs买哪个好_苹果12和苹果11哪个值得买-苹果12和11哪个更值得买

Ready 苹果iPhone 12系列产品已经开启预售&#xff0c;很多想要更换手机的伙伴都想知道&#xff0c;苹果12和11哪个更值得买呢&#xff1f; 本期视频是由iPhone 12、iPhone 11手机、iOS14系统录制的。 1.外观设计上 iPhone 11采用了圆润凸出的金属中框设计&#xff0c;而iPhone…

nginx的开始(一)---nginx的安装

文章目录 1.nginx是什么&#xff1f;2.nginx安装2.1.安装准备&#xff1a;2.2.进行安装&#xff1a;2.2.1.apt安装&#xff08;快速&#xff09;2.2.2.源码安装 2.3.配置文件简解&#xff08;nginx.conf&#xff09; 1.nginx是什么&#xff1f; Nginx&#xff08;发音为"e…

myBatis-plus之CRUD

文章目录 查询普通查询根据 ID 查询根据ID批量查询根据MAP查询 条件构造器查询构造器声明&#xff1a;QueryWrapper方法常用方法&#xff0c;以及简单使用方式实体作为条件构造器构造方法的参数lambda条件构造器 更新普通更新根据 ID 修改 条件构造器更新 删除普通删除根据 ID …