为什么 local::lib shell 代码使用 eval 和 $()

xen*_*ide 2 shell shell-script posix

使用local::lib需要你在你的~/.shellrc

eval $(perl -I$HOME/perl5/lib/perl5 -Mlocal::lib)
Run Code Online (Sandbox Code Playgroud)

我不明白使用eval, 并将语句封装在其中的意义$()是什么。我还注意到csh不需要你使用这些。所以我想知道有什么区别,以及我是否应该将它用于通用的 bourne shell 或zsh.

Gil*_*il' 5

perl -I$HOME/perl5/lib/perl5 -Mlocal::lib打印出一些shell代码。重点eval $(…)是在当前 shell 的上下文中执行该代码。这通常用于设置环境变量。您不能为此使用子流程,因为这只会影响子流程的环境。您可以获取一个片段:

. /path/to/snippet-containing-variable-definitions
Run Code Online (Sandbox Code Playgroud)

但这仅适用于生成变量值的代码是在 shell 中编写的。这里的代码是用 Perl 编写的,因此 Perl 代码生成 shell 代码。

dircolors使用相同的技术,许多其他程序也是如此。

shell 片段通常保持非常简单,只是变量赋值(带有用于值的纯字符串)和export语句,因此它们与所有 Bourne 风格的 shell(包括任何 POSIX shell)和 zsh 兼容。local::lib由于它export与赋值(POSIX 允许,但原始 Bourne shell 不允许)结合使用,因此与一些已有十年历史的系统毫无理由地不兼容。Csh 需要不同的语法;如果$SHELL包含csh作为子字符串,则 local::lib 发出 csh 语法。在 Windows 下,local::lib 生成等效的 cmd 语法;因为 cmd 没有等效的 .