为什么 (ps -f) 不创建子 shell,而是创建一个单独的进程?

Cur*_*Guy 4 unix linux shell

我需要一些帮助,因为我没有得到任何东西。根据我从互联网上读到的内容,当我们执行 shell 脚本或运行括号中的命令时,会创建一个子 shell:( )

我尝试使用仅包含以下命令的脚本对此进行测试:

ps -f
Run Code Online (Sandbox Code Playgroud)

当我运行它时,我看到以下结果:

ID      PID  PPID  C STIME TTY          TIME CMD 
me     2213  2160  0 08:53 pts/14   00:00:00 bash 
me     3832  2213  0 18:41 pts/14   00:00:00 bash 
me     3833  3832  0 18:41 pts/14   00:00:00 ps -f
Run Code Online (Sandbox Code Playgroud)

这很好,因为我看到我的 bash 进程已经为我的脚本生成了另一个 bash 进程。

但是当我这样做时:

( ps -f )
Run Code Online (Sandbox Code Playgroud)

它产生:

UID     PID  PPID  C STIME TTY          TIME CMD 
me     2213  2160  0 08:53 pts/14   00:00:00 bash 
me     3840  2213  0 18:46 pts/14   00:00:00 ps -f
Run Code Online (Sandbox Code Playgroud)

那么,如果括号生成一个子 shell,为什么它没有显示在进程中呢?为什么会ps -f被算作另一个进程呢?每个命令都作为单独的进程运行吗?

Fat*_*ror 5

看来您已经进行bash了一些优化。如果一个子 shell 只包含一个命令,为什么要让它成为一个子 shell?

$ ( ps -f )
UID        PID  PPID  C STIME TTY          TIME CMD
jovalko  29393 24133  0 12:05 pts/10   00:00:00 bash
jovalko  29555 29393  0 12:07 pts/10   00:00:00 ps -f
Run Code Online (Sandbox Code Playgroud)

但是,添加第二个命令:(例如 bash null 命令,它不执行任何操作),结果如下:

$ ( ps -f ; : )
UID        PID  PPID  C STIME TTY          TIME CMD
jovalko  29393 24133  0 12:05 pts/10   00:00:00 bash
jovalko  29565 29393  0 12:08 pts/10   00:00:00 bash
jovalko  29566 29565  0 12:08 pts/10   00:00:00 ps -f
Run Code Online (Sandbox Code Playgroud)

使用子 shell 的主要原因之一是您可以对一组命令而不是单个命令执行 I/O 重定向等操作,但如果您的子 shell 仅包含单个命令,则没有太多理由真正派生新的 bash 进程第一的。

至于ps计数作为一个过程,则有所不同。您使用的许多命令如lsgrepawk都是外部程序。但是,也有像cd,之类的内置函数kill

bash您可以使用以下命令确定当前是哪个命令type

$ type ps
ps is hashed (/bin/ps)
$ type cd
cd is a shell builtin
Run Code Online (Sandbox Code Playgroud)