x="a=b"
`echo $x`
echo $a

我希望第二行生成“ a = b”,并在主壳的上下文中执行它,从而导致新变量 a 有价值 b。但是,我真正得到的(如果我手动输入命令)是第二行之后的错误消息, bash: a=b: command not found

为什么呢?

有帮助吗?

解决方案

这是因为Bash解析命令行的顺序。它寻找可变定义(例如 a=b) 执行变量和命令替换(例如,在Backticks中命令)。因此,到了 echo $x 被取代 a=b, ,Bash将其视为可变定义为时已晚,而将其解析为命令。如果您只使用 $x 作为命令(而不是回声中的回声)。如 @mvds的答案一样 eval 命令可用于强制命令从一开始就被重新定制,这意味着它将被识别为变量定义:

$ x="a=b"
$ `echo $x`
-bash: a=b: command not found
$ $(echo $x)  # Exact same thing, but with cleaner syntax
-bash: a=b: command not found
$ $x  # This also does the same thing, but without some extra steps
-bash: a=b: command not found
$ eval "$x"  # This will actually work
$ echo $a
b
$ a=  # Start over
$ eval "$(echo "$x")"  # Another way of doing the same thing, with extra steps
$ echo $a
b

请注意,使用时 eval 我把所有的参考都提到了 $x 在双重报价中 - 这是为了防止bash解析的后期(例如单词拆分)发生 两次, ,由于Bash将完成其常规解析过程,然后认识到 eval 命令,然后重做整个解析过程 再次. 。从使用中获得意外结果真的很容易 eval, ,这至少消除了一些麻烦的潜力。

其他提示

尝试

eval $x

(我们需要30个字符才能发布此答案)

您的第一条回声线所做的是在子壳中运行,并将其值返回到Callee。 $() 顺便说一句 - 比背部更易于使用。

因此,您正在做的是首先运行 echo $x (返回 a=b)。而且,由于背景 a=b 将返回到试图运行该行作为命令的外壳,显然 - 不起作用。

在外壳中尝试一下:

$(echo ls)

您将清楚地看到正在发生的事情。

你试过了吗 $x 在那个有趣的撇号中?没有 echo, ,Echo似乎仅用于显示字符串,而不是执行命令。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top