首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何逃避历史扩展感叹号!一个双引号的字符串里?

如何逃避历史扩展感叹号!一个双引号的字符串里?
EN

Stack Overflow用户
提问于 2014-03-02 08:56:21
回答 4查看 8.7K关注 0票数 22

编辑:命令替换对于令人惊讶的行为并不是必要的,尽管它是最常见的用例。同样的问题也适用于echo "'!b'"

代码语言:javascript
复制
b=a

# Enable history substitution.
# This option is on by default on interactive shells.
set -H

echo '!b'
# Output: '!b'
# OK. Escaped by single quotes.

echo $(echo '!b')
# Output: '!b'
# OK. Escaped by single quotes.

echo "$(echo '$b')"
# Output: '$b'
# OK. Escaped by single quotes.

echo "$(echo '!b')"
# Output: history expands
# BAD!! WHY??
  • 在最后一个示例中,规避!的最佳方法是什么?
  • 为什么即使我使用单引号(而echo "$(echo '$b')"是单引号),它也没有逃脱呢?!$有什么区别?
  • 为什么echo $(echo '!b') (没有引号)起作用?(由@MBlanc指出)。

我宁愿这样做而不:

  • set +H,因为之后我需要set -H来维护shell状态。
  • 反斜杠转义,因为每一个!我都需要一个反斜杠,它必须在引号之外: 回显$( echo '!a')“#!a‘。不太好。回音$(回叫'a '!‘B '!’C‘)#a!B!C#很好,但很详细。
  • echo $(echo '!b') (没有引号),因为命令可以返回空格。

版本:

代码语言:javascript
复制
bash --version | head -n1
# GNU bash, version 4.2.25(1)-release (i686-pc-linux-gnu)
EN

回答 4

Stack Overflow用户

回答已采纳

发布于 2014-03-02 17:19:42

在最后一个例子中,

代码语言:javascript
复制
echo "$(echo '!b')"

感叹号不是单引号。因为历史扩展发生在解析过程的早期,所以单引号只是双引号字符串的一部分;解析器还没有识别命令替换以建立一个新的上下文,其中单引号将引用操作符。

要解决这个问题,您必须暂时关闭历史扩展:

代码语言:javascript
复制
set +H
echo "$(echo '!b')"
set -H
票数 23
EN

Stack Overflow用户

发布于 2016-12-22 00:04:17

这被反复报告为一个bug,最近一次是在2014年针对bash4.3,因为行为可以追溯到bash 3。

有一些讨论,这是一个错误,或预期,但可能是不受欢迎的行为;似乎大家的共识是,无论你想要描述的行为,它不应该被允许继续。

它在bash4.4中是固定的,echo "$(echo '!b')"没有展开,echo "'!b'"有,我认为这是正确的行为,因为单引号是第一个示例中的shell语法标记,而不是第二个示例中的shell语法标记。

票数 4
EN

Stack Overflow用户

发布于 2014-03-02 11:17:00

如果启用了历史扩展,则只有将!字符放入单引号、转义或后跟空格字符、回车或=时才能回显它。

来自man bash

代码语言:javascript
复制
   Only backslash (\) and single quotes can  quote  the  history
   expansion character.

   Several  characters inhibit history expansion if found immediately fol-
   lowing the history expansion character, even if it is unquoted:  space,
   tab,  newline,  carriage return, and =.

我相信这里的关键词是“只有”。问题中提供的例子只考虑最外层的引号是双引号。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/22125658

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档