切勿将`-a`或`-o`运算符与`[`


11

斯特凡·查泽拉斯写道:

一些规则,例如

  • 总是引用变量
  • 永远不要使用-aor -o运算符(使用多个[命令以及&&and和||shell运算符)

[使用POSIX shell 使其可靠。

为什么“从不使用-aor -o运算符”?

我该如何“使用几个[命令以及&&and和||shell运算符”?

Answers:


13

为什么“从不使用-aor -o运算符”?

由于它们可能含糊不清,因此不符合POSIX

指定-a和-o二进制基元以及'('和')'运算符的XSI扩展已被标记为过时。(根据所评估的特定表达式,语法会模糊地定义许多使用它们的表达式。)使用这些表达式的脚本应转换为下面给出的形式。尽管许多实现将继续支持这些过时的形式,但是在处理用户提供的输入时,脚本应格外小心,这些输入可能与这些以及其他主操作符和运算符相混淆。除非应用程序开发人员知道产生脚本输入的所有情况,否则调用将类似:

test "$1" -a "$2"

应写为:

test "$1" && test "$2"

我该如何“使用几个[命令以及&&and和||shell运算符”?

通过执行多个测试并使用所述运算符将它们链接起来;例如:

[ 0 -eq 0 -a \( 0 -eq 1 -o 1 -eq 1 \) ]

可以重写为等效的:

[ 0 -eq 0 ] && ([ 0 -eq 1 ] || [ 1 -eq 1 ])

或更好:

[ 0 -eq 0 ] && { [ 0 -eq 1 ] || [ 1 -eq 1 ]; }

谢谢。(1)“'('和')'运算符已被标记为过时”。是()将命令分组的操作员吗?如果它们已过时,它们的替代品是什么?(2)应该test "$1" -a "$2"test "$1" && test "$2"或代替((test "$1" && test "$2"))吗?我们不需要((..))吗?
蒂姆(Tim)

@Tim查看更新。(1)是-您可以使用(){}作为替代。(2)第一个;(())是用于算术扩展的,此处您要测试测试链的退出状态,因此可以将测试分组在子shell ()或当前shell中{}
kos

谢谢。我认为我的问题可能超出了这篇文章。因此,我将其发布在新帖子中。
蒂姆(Tim)

1
@Tim使用(and )运算符的唯一原因是在使用-aor时-o。由于后者已过时,因此显然也不再需要前者。
Barmar
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.