5

我想决定是否总是省略 Bash[[测试中出现的变量的引号。我将man页面解释为可以在不损失任何正确性的情况下这样做。


我设计了这个简单的“测试”来验证我的想法和“预期的行为”,但它可能完全证明不了,看看它:

x='1 == 2 &&'; if [[ $x == '1 == 2 &&' ]]; then echo yes; else echo no; fi

注意我不是这样写的:

x='1 == 2 &&'; if [[ "$x" == '1 == 2 &&' ]]; then echo yes; else echo no; fi

到目前为止,这一直是我的风格,如果没有别的,那就是为了保持一致性。


将我的编码约定切换为始终省略[[测试中出现的变量的引号是否安全?

我正在尝试学习 Bash,并且正在努力培养良好的习惯、良好的风格和正确性。

4

2 回答 2

9

要记住的关键是模式匹配上下文中的引号和转义总是会导致它们的内容变成文字。==从来没有必要在inside 的左侧引用[[,只有右侧被解释为模式。如果您想要文字匹配并避免解释变量中的模式元字符,则必须在右侧引用。

换句话说,[ "$x" = "$x" ][[ $x == "$x" ]]大多是等价的,当然在 Bash 中应该首选后者。

一个快速提示:认为复合命令的运算符[[ ]]语法上与其他控制运算符相同,例如elif, do, ;;, and ;;&(尽管在技术上在手册中它们属于自己的类别)。它们实际上是复合命令部分的分隔符,这就是它们如何实现看似神奇的特性,例如短路扩展的能力。这应该有助于澄清 的许多行为[[,以及为什么它不同于例如算术运算符,它们不是那样的。

更多示例: http: //mywiki.wooledge.org/BashFAQ/031#Theory

于 2013-03-22T22:57:55.373 回答
5

不,你不应该养成总是省略引号的习惯,即使它们出现在[[测试中。Bash 因不引用引号而燃烧人们而闻名:-)

在 bash 中,[[ ]]应该始终评估为表达式,因此脚本将继续运行。风险在于逻辑错误可能会在不经意间弹出。在我能想到的所有情况下,这都很好。但是,引号可以让您具体说明您想要什么,并且除了更安全之外还可以自我记录。

考虑这个表达式:

if [[ "$INT" =~ ^-?[0-9]+$ ]]; then

它仍然可以在没有引号的情况下工作,因为它介于两者之间[[ ]],但引号是澄清的并且不会引起任何问题。

无论如何,这是我作为一个在 Bash 手上接受了皇家软管的人的看法,因为我没有" "解决需要他们的东西:'(

我的 bash 黑客朋友曾经说过,“在 Bash 中自由地使用引号”。这个建议对我很有帮助。

于 2013-03-22T22:37:31.110 回答