bash shell还提供了3个可在if-then语句中使用的高级特性。
- 在子shell中执行命令的单括号。
- 用于数学表达式的双括号。
- 用于高级字符串处理功能的双方括号。
接下来将详细描述各个特性。
使用单括号
单括号允许在if语句中使用子shell。单括号形式的test命令格式如下:
(command)
在bash shell执行command之前,会先创建一个子shell,然后在其中执行命令。如果命令成功结束,则退出状态码会被设为0,then部分的命令就会被执行。如果命令的退出状态码不为0,则不执行then部分的命令。来看一个使用子shell进行测试的例子:
$ cat SingleParentheses.sh
#!/bin/bash
# Testing a single parentheses condition
#
echo $BASH_SUBSHELL
#
if (echo $BASH_SUBSHELL)
then
echo "The subshell command operated successfully."
#
else
echo "The subshell command was NOT successful."
#
fi
$
$ ./SinglePArentheses.sh
01
The subshell command operated successfully.
当脚本第一次(在if语句之前)执行echo $BASH_SUBSHELL命令时,是在当前shell中完成的。该命令会输出0,表明没有使用子shell。在if语句内,脚本在子shell中执行echo $BASH_SUBSHELL命令,该命令会输出1,表明使用了子shell。子shell操作成功结束,接下来是执行then部分的命令。
警告 当你在if test语句中使用进程列表时,可能会出现意料之外的结果。哪怕进程列表中除最后一个命令之外的其他命令全都失败,子shell仍会将退出状态码设为0,then部分的命令将得以执行。
对脚本略作修改,来看一个在子shell中执行失败的例子:
$ cat SingleParentheses.sh
#!/bin/bash
# Testing a single parentheses condition
#
echo $BASH_SUBSHELL
#
if (cat /etc/PASSWORD)
then
echo "The subshell command operated successfully."
#
else
echo "The subshell command was NOT successful."
#
fi
$
$ ./SinglePArentheses.sh
cat: /etc/PASSWORD: NO such file or directory
The subshell command was NOT successful.
因为子shell中的命令指定了错误的文件名,所以退出状态码被设为非0。接下来则执行else部分的命令。
使用双括号
双括号命令允许在比较过程中使用高级数学表达式。test命令在进行比较的时候只能使用简单的算术操作。双括号命令提供了更多的数学符号,这些符号对有过其他编程语言经验的程序员而言并不陌生。双括号命令的格式如下:
((expression))
expression可以是任意的数学赋值或比较表达式。除了test命令使用的标准数学运算符,表还列出了双括号中可用的其他运算符。
符号 | 描述 |
---|---|
val++ | 后增 |
val-- | 后减 |
++val | 先增 |
--val | 先减 |
! | 逻辑求反 |
~ | 位求反 |
** | 幂运算 |
<< | 左位移 |
>> | 右位移 |
& | 位布尔AND |
| | 位布尔OR |
&& | 逻辑AND |
|| | 逻辑OR |
双括号命令既可以在if语句中使用,也可以在脚本中的普通命令里用来赋值:
$ cat DoubleParentheses.sh
#!/bin/bash
# Testing a double parentheses command
#
val1=10
#
if (( $val1 ** 2 > 90 ))
then
(( val2 = $val1 ** 2 ))
echo "The square of $val1 is $val2,"
echo "which is greater than 90."
#
fi
$
$ ./DoubleParentheses.sh
The square of 10 is 100,
which is greater than 90.
注意,双括号中表达式的大于号不用转义。这是双括号命令又一个优越性的体现。
使用双方括号
双方括号命令提供了针对字符串比较的高级特性。双方括号的格式如下:
[[ expression ]]
expression可以使用test命令中的标准字符串比较。除此之外,它还提供了test命令所不具备的另一个特性——模式匹配。
注意 双方括号在bash shell中运行良好。不过要小心,不是所有的shell都支持双方括号。
在进行模式匹配时,可以定义通配符或正则表达式来匹配字符串:
$ cat DoubleBrackets.sh
#!/bin/bash
# Using double brackets for pattern matching
#
#
if [[ $BASH_VERSION == 5.* ]]
then
echo "You are using the Bash Shell version 5 series."
fi
$
$ ./DoubleBrackets.sh
You are using the Bash Shell version 5 series.
上述脚本中使用了双等号(==)。双等号会将右侧的字符串(5.*)视为一个模式并应用模式匹配规则。双方括号命令会对$BASH_VERSION环境变量进行匹配,看是否以字符串5.起始。如果是,则测试通过,shell会执行then部分的命令。