Oli*_*Oli 144 command-line bash
每隔一段时间,我就会敲出一个 bash 脚本,它让我觉得有几种设置变量的方法:
key=value
env key=value
export key=value
Run Code Online (Sandbox Code Playgroud)
当您在脚本或单个命令中时(例如,我经常将变量与 Wine 启动器链接起来以设置正确的 Wine 前缀),这些似乎是完全可以互换的,但肯定不是这种情况。
这三种方法有什么区别,你能举个例子说明我什么时候特别想使用每种方法吗?
肯定与`VAR=...` 和 `export VAR=...` 有什么区别?但我也想知道如何env
适应这个,一些展示每个好处的例子也很好:)
Jan*_*ary 135
让我们考虑一个具体的例子。该grep
命令使用一个名为的环境变量GREP_OPTIONS
来设置默认选项。
现在。鉴于该文件test.txt
包含以下几行:
line one
line two
Run Code Online (Sandbox Code Playgroud)
运行命令grep one test.txt
将返回
line one
Run Code Online (Sandbox Code Playgroud)
如果您使用该-v
选项运行 grep ,它将返回不匹配的行,因此输出将是
line two
Run Code Online (Sandbox Code Playgroud)
我们现在将尝试使用环境变量设置选项。
没有export
设置的环境变量不会在您调用的命令的环境中被继承。
GREP_OPTIONS='-v'
grep one test.txt
Run Code Online (Sandbox Code Playgroud)
结果:
line one
Run Code Online (Sandbox Code Playgroud)
显然,该选项-v
没有传递给grep
。
当您设置一个仅供 shell 使用的变量时,您希望使用这种形式,例如在for i in * ; do
您不想导出$i
.
但是,该变量会传递到该特定命令行的环境中,因此您可以执行
GREP_OPTIONS='-v' grep one test.txt
Run Code Online (Sandbox Code Playgroud)
这将返回预期
line two
Run Code Online (Sandbox Code Playgroud)
您可以使用此表单临时更改已启动程序的此特定实例的环境。
导出变量会导致该变量被继承:
export GREP_OPTIONS='-v'
grep one test.txt
Run Code Online (Sandbox Code Playgroud)
现在返回
line two
Run Code Online (Sandbox Code Playgroud)
这是在 shell 中设置变量以使用随后启动的进程的最常见方法
这一切都是在 bash 中完成的。export
是一个内置的 bash;VAR=whatever
是 bash 语法。env
另一方面,它本身就是一个程序。当env
被调用时,会发生以下事情:
env
作为新进程执行env
改变环境,和env
过程由替换command
过程。示例:
env GREP_OPTIONS='-v' grep one test.txt
Run Code Online (Sandbox Code Playgroud)
此命令将启动两个新进程:(i) env 和 (ii) grep(实际上,第二个进程将替换第一个进程)。从grep
过程来看,结果和running完全一样
GREP_OPTIONS='-v' grep one test.txt
Run Code Online (Sandbox Code Playgroud)
但是,如果您不在 bash 中或不想启动另一个 shell(例如,当您使用exec()
函数系列而不是system()
调用时),则可以使用此习惯用法。
#!/usr/bin/env
这也是为什么使用习语#!/usr/bin/env interpreter
而不是#!/usr/bin/interpreter
. env
不需要程序的完整路径,因为它使用execvp()
函数搜索PATH
变量,就像 shell 一样,然后用 命令 run替换自身。因此,它可用于找出解释器(如 perl 或 python)在路径上的“位置”。
这也意味着通过修改当前路径,您可以影响将调用哪个 python 变体。这使得以下成为可能:
echo -e '#!/usr/bin/bash\n\necho I am an evil interpreter!' > python
chmod a+x ./python
export PATH=.
python
Run Code Online (Sandbox Code Playgroud)
而不是运行 Python,将导致
I am an evil interpreter!
Run Code Online (Sandbox Code Playgroud)