为什么破折号以不同的方式扩展\\\\?

Modified on: Sat, 30 Jun 2018 04:25:30 +0800

我有一个小小的开源项目,出于各种原因,我试图用合理的可移植shell脚本编写。它的自动化集成测试检查路径表达式中的恶意字符是否得到了正确处理等等。

/bin/sh提供的bash的用户看到测试失败,我已将其简化为以下内容:

echo "A bug\\'s life"
echo "A bug\\\\'s life"

在bash上,它产生了预期的结果:

A bug\'s life
A bug\\'s life

我用它制作的破折号就是这样做的:

A bug\'s life
A bug\'s life

我想我没有在破折号中找到一个错误,我可能会错过一些东西。对此有合理的解释吗?

最佳答案

echo "A bug\\'s life"

因为它们是双引号,并且\在双引号内是特殊的,所以shell将第一个\理解为转义 / < em>引用第二个\。所以A bug\'s life参数被传递给echo

echo "A bug\'s life"

本来会完全一样。 '在双引号内不是特殊的,\不会被删除,所以它是传递给echo的完全相同的参数。

正如在为什么printf比echo更好?中所解释的,echo实现。

dash之类的符合Unix的实现中,\用于引入转义序列:\n for newline,\b用于退格键,\0123用于八进制序列...和\\用于反斜杠本身。

某些(非POSIX)选项需要-e选项,或者仅在符合模式时执行(例如bash时使用右侧构建) OS / X的sh或在环境中使用SHELLOPTS=xpg_echo调用时的选项。

所以在标准中(仅限Unix标准; POSIX保留未指定的行为)echo s,

echo '\\'

同样如下:

echo "\\\\"

输出一个反斜杠,而在bash中则不符合一致性模式:

echo '\\'

将输出两个反斜杠。

最好避免echo并使用printf

$ printf '%s\n' "A bug\'s life"
A bug\'s life

在所有printf实现中,此实例中的工作方式相同。


相关问答

添加新评论