首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >与仅仅计算变量相比,eval/bash -c的意义是什么?

与仅仅计算变量相比,eval/bash -c的意义是什么?
EN

Stack Overflow用户
提问于 2015-12-23 01:22:24
回答 2查看 851关注 0票数 9

假设将以下命令存储在变量中:

代码语言:javascript
运行
复制
COMMAND='echo hello'

有什么区别

代码语言:javascript
运行
复制
$ eval "$COMMAND"
hello

$ bash -c "$COMMAND"
hello

$ $COMMAND
hello

?为什么上一个版本几乎从来没有使用过,如果它是较短的和(据我所能看到)做完全相同的事情?

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2015-12-23 02:06:56

第三种形式一点也不像其他两种形式--但是要理解为什么,我们需要在解释命令时按照bash的操作顺序,看看在使用每种方法时都遵循了哪些操作。

Bash解析阶段

  1. 报价处理
  2. 分裂成命令
  3. 特殊运算符解析
  4. 扩张
  5. 分词
  6. 球状
  7. 执行

使用eval "$string"

eval "$string"遵循从#1开始的所有上述步骤。

  • 字符串中的文字引号变成语法引号。
  • >()这样的特殊运算符被处理。
  • $foo这样的扩展是受尊重的。
  • 这些扩展的结果在字符上被分割成单独的单词。
  • 如果这些单词解析为相同并具有可用的匹配,则这些单词被扩展为globs,最后执行命令。

使用sh -c "$string"

...performs和eval一样,但是在作为单独进程启动的新shell中;因此,当这个新进程退出时,对变量状态、当前目录等的更改将过期。(还请注意,新shell可能是支持不同语言的不同解释器;即。sh -c "foo"将不支持与bashkshzsh等相同的语法)。

使用$string

...starts在步骤5,“分词”。

这是什么意思?

引号不受尊重。

因此,printf '%s\n' "two words"将解析为printf %s\n "two words",而不是printf %s\n two words的通常/预期行为(其中的引号由shell使用)。

拆分为多个命令(在;s、&或类似的命令上)不会发生。

因此:

代码语言:javascript
运行
复制
s='echo foo && echo bar'
$s

...will发出以下输出:

代码语言:javascript
运行
复制
foo && echo bar

如果不是这样的话,就会出现以下...instead:

代码语言:javascript
运行
复制
foo
bar

特殊运算符和扩展不受尊重。

没有$(foo),没有$foo,没有<(foo)等等。

重定向不受尊重。

>foo2>&1只是由字符串拆分创建的另一个单词,而不是shell指令。

票数 12
EN

Stack Overflow用户

发布于 2015-12-23 01:32:11

至少有一些时候他们是不同的。请考虑以下几点:

代码语言:javascript
运行
复制
$ cmd="echo \$var"
$ var=hello
$ $cmd
$var
$ eval $cmd
hello
$ bash -c "$cmd"

$ var=world bash -c "$cmd"
world

它显示了执行变量展开的不同点。如果我们先做set -x就更清楚了

代码语言:javascript
运行
复制
$ set -x
$ $cmd
+ echo '$var'
$var
$ eval $cmd
+ eval echo '$var'
++ echo hello
hello
$ bash -c "$cmd"
+ bash -c 'echo $var'

$ var=world bash -c "$cmd"
+ var=world
+ bash -c 'echo $var'
world

我们在这里可以看到查尔斯·达菲在他出色的回答中谈到的很多内容。例如,试图直接执行变量时会打印$var,因为参数展开和前面的步骤已经完成,因此我们不能像对eval那样获得var的值。

bash -c选项只从父shell继承exported变量,而且由于我没有导出var,所以它对新shell不可用。

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

https://stackoverflow.com/questions/34427146

复制
相关文章

相似问题

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