标签:
在上文中曾说到:
本文中继续深入讲三点:
如果有两个同名的环境变量,很简单,那么后面的值会覆盖前面的:
$ env foo=1 foo=2 bash -c ‘echo $foo‘ 2 |
上篇文章中我们没有提到过函数,Bash 其实是可以从环境变量中导入函数的,比如下面这样:
$ foo() { echo foo函数; } $ export -f foo $ bash $ foo foo函数 |
上一级的 Shell 把函数传给了它的 child shell,Bash 是怎么实现的呢?我们用 env 命令演示一下:
$ env ‘BASH_FUNC_foo%%=() { echo foo函数; }‘ bash -c ‘foo‘ foo函数 |
其实 Bash 就是把满足 "BASH_FUNC_函数名%%=(){ 函数体" 格式的环境变量作为函数源码解析并导入。所以两个同名的变量和函数并不会冲突,可以同时导入,像这样:
$ env ‘foo=1‘ ‘BASH_FUNC_foo%%=() { echo $1; }‘ bash -c ‘foo $foo‘ 1 |
既然可以同时导入,那么导出更没问题了:
$ foo=1 $ foo(){ echo foo函数; } $ export foo;export -f foo $ env ... foo=1 BASH_FUNC_foo%%=() { echo foo函数 } ... |
注意,本文所讲的表现仅适用于 Bash 4.3.30 及之后的版本,之前的 Bash 版本在导出函数时不会给函数名加上 BASH_FUNC_ 前缀和 %% 后缀,在导入时也不会识别前缀后缀,只要看到 = 右边是 "() {" 这四个字符,就按函数导入,像这样:
$ env ‘foo=() { echo foo函数; }‘ bash -c ‘foo‘ foo函数 |
由于环境变量字符串的转换和识别规则不同,假如你在 Bash 4.3.30 中打开一个 Bash 3.2.25,后者是无法继承到前者导出的函数的:
$ bash4.3.30 $ foo() { echo foo函数 ; } $ export -f foo $ bash3.2.25 $ foo bash3.2.25: foo: command not found |
反之亦然,同时 foo 会被导入成一个变量:
$ bash3.2.25 $ foo() { echo foo函数 ; } $ export -f foo $ bash4.3.30 $ foo bash3.2.25: foo: command not found $ echo $foo () { echo foo函数 } |
标签:
原文地址:http://www.cnblogs.com/ziyunfei/p/4828767.html