为什么bash没有按照短路命令的顺序来停止错误?

我看到一些行为,当我用-e选项运行一个bash脚本时,这个行为对我来说没有任何意义。这个选项有多个与&& s &&的命令,其中一个失败了。 我希望脚本停止在失败的命令上,并返回退出状态,而是只是愉快地执行脚本的其余部分。

以下是对我有意义的例子:

 $ false && true; echo $? 1 $ bash -xe -c "false && true"; echo $? + false 1 $ bash -xe -c "false; true"; echo $? + false 1 

这是对我没有意义的一个:

 $ bash -xe -c "false && true; true"; echo $? + false + true 0 

这是我不明白是怎么回事。 false && true返回状态1,所以脚本不应该停止执行并返回状态1,就像脚本为false; true false; true

在进行实验时,我发现如果我用圆括号包围命令链,它的工作方式就如我所料:

 $ bash -xe -c "(false && true); true"; echo $? + false 1 

有人可以解释一下吗?

这里的逻辑是你使用&&已经错误检查了。 bash不会将if条件中的失败视为值得中止,即使使用set -e

当你将这些命令包装在一个括号中时,实际上是在一个子shell中运行这些命令,所以脚本本身只会看到这个子shell的返回,即:它根本不知道&&是否涉及到,所以它会中止期望。

请参考参考手册:

如果失败的命令是命令列表的一部分,那么shell将不会立即退出,直到关键字,if语句中的测试的一部分,以及在&&或||中执行的任何命令的一部分。 除了最后的&&或||之后的命令,管道中的最后一个命令,或者命令的返回状态与!