为什么以下代码段不起作用?
set -ue
inc=0
((inc++))
((inc++))
echo $inc
echo Here
[output nothing, return code 1]
Run Code Online (Sandbox Code Playgroud)
但是当禁用'-e'时它确实按预期工作?我用"GNU bash,版本4.3.46(1)-release"运行它
因此(来自bash手册页):
((表达))
根据ARITHMETIC EVALUATION下面描述的规则评估表达式.如果表达式的值不为零,则返回状态为0; 否则返回状态为1.这与let"expression"完全相同.
所以,当inc是0你运行:
((inc++))
Run Code Online (Sandbox Code Playgroud)
...表达式的值是0(因为您正在使用后缀++运算符),因此返回值为1,这意味着您的脚本-e在生效时退出.解决此特定问题的最简单方法是使用前缀++运算符:
set -ue
inc=0
((++inc))
((++inc))
echo $inc
echo Here
Run Code Online (Sandbox Code Playgroud)
更新
正如@cdarke所提到的,您可以改为使用:命令,这是一个特殊的shell命令,意味着"除了评估所有参数之外什么都不做".您将经常在shell脚本中遇到这种情况,它用于变量默认值,如下所示:
: ${SOMEVAR:=somevalue}
Run Code Online (Sandbox Code Playgroud)
或者在while循环中,像这样:
while :; do
...
done
Run Code Online (Sandbox Code Playgroud)
所以代替:
((inc++))
Run Code Online (Sandbox Code Playgroud)
你可以这样做:
: $((inc++))
Run Code Online (Sandbox Code Playgroud)
但是你会发现有两处变化(这就是为什么我在原来的答案中没有提到它).因为:它本身就是一个命令,所以你不能再单独使用((...))语法(这完全等同于let命令).相反,您需要使用算术表达式语法$((...)).
你也可以这样做:
((inc++)) || true
Run Code Online (Sandbox Code Playgroud)
甚至:
((inc++)) || :
Run Code Online (Sandbox Code Playgroud)
其同样具有从表达式中抑制错误返回码的效果.