在 bash 中,您可以通过两种不同的方式将字符串视为命令(并运行它):
#!/bin/bash
cmd="echo -n sometext"
eval $cmd # Not sure if quotes make a difference here
和
#!/bin/bash
cmd="echo -n sometext"
$cmd # Not sure if quotes make a difference here either
两者之间有什么区别吗?是否有报价cmd
有所作为的情况?性能如何?
是的,:) 您需要首先了解eval
的工作原理。基本上,eval
是一个 shell 内置命令。传递给eval
的任何参数首先被视为字符串。 让我们举个例子:
cmd="echo -n sometext"
eval $cmd
此命令的完整运行过程如下:
eval $cmd
+ eval echo -n sometext
++ echo -n sometext
sometext
在这里,首先$cmd首先被评估,然后将整个字符串作为参数传递给 eval 命令。然后 eval 计算命令,将第一个参数视为"命令或可执行文件",然后作为普通命令运行。因此,这里要执行 2 轮评估以执行完整的命令。 (注意:上面的+
符号显示了在bash -x
模式下使用时的逐步执行)
主要后果在于变量膨胀。有了eval
,我们有两轮扩张。当然,一个是在定义cmd
时,另一个是在执行eval
时。
var="inital"
cmd="echo -n $var $var"
var="chanded in the mean time"
eval $cmd
inital chanded in the mean time
但是,当您只使用$cmd
而不使用 eval 时,bash 会处理从变量扩展到最终执行的所有事情。只需在仅运行时查看调试窗口详细信息$cmd
$cmd
+ echo -n sometext
sometext
性能方面,直接使用$cmd
就足够了。但是,当您尝试使用某些外部命令或需要更改环境的脚本时,可以使用eval
在cmd="echo -n sometext"
中,引号是必需的,否则在"echo"之后,bash 会引发如下错误:
cmd=echo -n sometext
-n: command not found
我希望解释会有所帮助。