转载自:https://blog.csdn.net/Code_LT/article/details/127355288

子shell的概念 中文翻译过来的“子shell”叫法,实际上包括了“subshell”和“child shell”。

subshell是指: 对父shell的一个拷贝,共享了父shell的变量,函数,别名等,能用但修改只在subshell中生效。通过()开启subshell。内置变量BASH_SUBSHELL显示subshell的层数。

child shell是指: 重新开启的一个shell,不共享父shell的变量,函数,别名。一个纯新的环境。命令bash或者运行脚本就开启child shell。内置变量SHLVL显示child shell的层数。

The Korn Shell: Unix & Linux Programming Manual : A subshell is a separate copy of the parent shell, so variables, functions, and aliases from the parent shell are available to the subshell

BASH_SUBSHELL

echo $BASH_SUBSHELL 0(echo $BASH_SUBSHELL) 1 --进入1层 subshell ( ( ( ( (echo $BASH_SUBSHELL) ) ) ) ) 5 --进入5层 subshell bash echo $SHLVL 1 --进入1层 child shell echo $BASH_SUBSHELL 0bash echo $SHLVL 2 --进入2层 child shell echo $BASH_SUBSHELL 01 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 一、进入子shell的方式 直接输入bash(退出 :exit,也无法继承和改变父shell中的普通变量,同脚本):child shell ()中的命令是在子shell中实现:subshell 运行脚本,脚本也是在子shell中实现 :child shell 二、差异 child shell是一个全新的环境,不共享父shell中的普通变量,普通变量只能通过export方式实现共享。

subshell 中的普通变量是可以从父shell中继承的,只是不能改变父shell中的变量值。

验证环境:

cat /proc/version Linux version 3.0.101-0.47.55-default (geeko@buildhost) (gcc version 4.3.4 [gcc-4_3-branch revision 152973] (SUSE Linux) ) #1 SMP Thu May 28 08:25:11 UTC 2015 (dc083ee) 1 2 ()的表现: x=10 echo $x 10 echo $$ #该命令用于显示当前shell进程号 10497 --父shell的进程号 (echo $$;echo $x;ps;x=5;echo $x) 10497 -- 实际上还是父shell的进程 10 -- 进程中的x可取父进程中的x 5 -- 进程中的x被改变 PID TTY TIME CMD 3757 pts/0 00:00:00 bash #subshell进程进程号 3758 pts/0 00:00:00 ps 10497 pts/0 00:00:00 bash #父进程进程号 echo $x 10 -- 父进程中的x没有改变 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 bash命令 bash #进入子shell echo $$ 3609 ps PID TTY TIME CMD 3609 pts/0 00:00:00 bash --child shell进程 5359 pts/0 00:00:00 ps 10497 pts/0 00:00:00 bash echo $x -- 空 x=5;echo $x 5 exit #退出子进程 echo $$ 10497 --回到父shell echo $x 10 -- 父shell中x没有改变

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 脚本中子shell的表现: 将echo $$;echo $x;ps;x=5;echo $x写入test.sh中

echo $x 10 ./test.sh 8794 --子shell的进程号 -- 无法获取父shell中的变量值 PID TTY TIME CMD 8794 pts/0 00:00:00 sh -- child shell 进程 8795 pts/0 00:00:00 ps 10497 pts/0 00:00:00 bash 5 -- 子shell中定义的变量

echo $x 10 --父shell中值不变 1 2 3 4 5 6 7 8 9 10 11 12 13 三、差异的原因 ()的子shell能获取父shell中变量值的原因因为是subshell,$()一样能够获取到父shell中变量的值。$()命令的()表现和单独的()一样,也是在子shell中运行,但能访问父shell变量,但不能改变父shell变量。

参考: https://stackoverflow.com/questions/19462291/bash-subshell-parentheses-vs-dollar-parentheses https://tldp.org/LDP/abs/html/subshells.html

https://www.cnblogs.com/ziyunfei/p/4803832.html