首页 Shell subshell
文章
取消

Shell subshell

source

source 有点类似于 C/C++ 的 #include 预处理指令,也就是 文件包含

source a.sh,解释器执行到此处时,会在当前进程解释执行a.sh的内容。

从效果上看,等价于将此语句替换为a.sh的文件内容,因此和#include很相似。

可以利用此特性,将一些通用代码提取到公共文件,然后在用的时候source一下。

source 还有个别名 .,在 bash 中,它们是同义词,但在其他 shell,可能只有 .

subshell

subshell子shell 的意思;一个shell进程,可以通过fork系统调用来创建一个subshell

因为是 fork 创建的,所以 subshell 的数据与其 父shell 相同,环境变量这些进程属性也相同。

由于 subshell 是独立进程,所以在 subshell 中无法修改 父shell 的数据,如变量、环境变量。

如某段代码需执行 cd,但又不希望影响当前进程的 cwd,就可以将其放到 subshell 去执行。

产生方式

  • (commands...):命令分组
  • $(commands...):命令替换
  • `commands...`:命令替换
  • shell语句后加上&(异步),如{ foo; bar; } &,对应语句将在subshell执行
  • shell语句是管道的一端(或两端),如foo | while ...,while循环将在subshell执行

$BASHPID

我们知道,在 shell 中,可以使用 $$ 来获取当前 shell 进程的 pid。

但是,在 subshell 中,$$ 的值并没有被改变,而是原样 fork 了过来:

1
2
3
4
5
6
7
8
9
$ echo $$
16421

$ (echo $$)
16421

$ echo a=$$ 1>&2 | echo b=$$ 1>&2
a=16421
b=16421

如果我们需要获取 subshell 自己的 pid,可以使用 $BASHPID 特殊变量:

1
2
3
4
5
6
7
8
9
$ echo $$ $BASHPID
16421 16421

$ (echo $$ $BASHPID)
16421 18670

$ echo a=$$ x=$BASHPID 1>&2 | echo b=$$ y=$BASHPID 1>&2
a=16421 x=18671
b=16421 y=18672
本文由作者按照 CC BY 4.0 进行授权

Shell 管道

Shell 特殊字符