有什么区别
echo "Hello " ; echo "world"
和
echo "Hello " && echo "world"
两者似乎都在彼此之后运行这两个命令。
答案1
echo "Hello" ; echo "world"
echo "world"
表示无论前一个命令的退出状态如何,都顺序运行echo "Hello"
。换句话说,echo "world"
无论先前命令成功或失败,都会运行echo "Hello"
。
在 的情况下echo "Hello" && echo "world"
,仅当第一个命令 ( ) 成功(即退出状态 0)echo "world"
时才会运行。echo "Hello"
这就是所谓的短路评估。
以下示例显示 shell 如何处理具有不同运算符的命令链:
$ false ; echo "OK"
OK
$ true ; echo "OK"
OK
$ false && echo "OK"
$ true && echo "OK"
OK
$ false || echo "OK"
OK
$ true || echo "OK"
$
最后一个案例没有打印,OK
因为它被 短路了true
。
简而言之,;
是分隔符,&&
是逻辑与,||
是逻辑或(阅读更多这里)。
答案2
Linux 中的每个命令在完成运行时都会返回一个退出代码。退出代码被分配给一个特殊变量?
,因此您可以轻松检查最后一个命令的状态,例如通过echo $?
。这经常在脚本中使用。如果命令成功完成,则返回退出代码 0,而如果执行期间出现任何错误,则退出状态为非零。请参阅下面的示例:
$ 回显“你好” 你好 $回声$? 0 $ rm 不存在的文件 rm:无法删除“不存在的文件”:没有这样的文件或目录 $回声$? 1
现在,这引出了你的问题。这&&
是一个特殊的运算符,它表示“仅当上一个命令成功时才执行下一个命令,即返回退出代码为零”。还有一个反向运算符||
,如果前一个命令失败,即以非零值退出,则仅执行后一个命令。请参阅下面的示例:
$ echo "Hello" && echo "上一个命令成功" 你好 上一个命令成功 $ rm nonexistent-file && echo "这不会被打印" rm:无法删除“不存在的文件”:没有这样的文件或目录 $ rm 不存在的文件 || echo“但这将会被显示” rm:无法删除“不存在的文件”:没有这样的文件或目录 但这会显示
编辑:问题是关于两者之间的差异&&
,;
因此为了成为完整的答案,我需要添加分号只是将一个命令与另一个命令分开。不会检查退出代码,因此如果您有多个用分号分隔的命令,它们只是按顺序执行,即一个接一个地执行,彼此完全独立。
答案3
此外@heemayl 的回答,&&
(以及||
)将导致 shell 只处理单身的所有链接命令的退出代码。因此,如果您有trap [...] ERR
orset -o errexit
行,它将在执行退出代码处理之前处理所有命令。