两者exec
都env
不要分叉,请参见以下示例:
docker run --rm -it ubuntu:18.04 sh -c 'exec sleep 1 & ps -Ho pid,ppid,cmd'
PID PPID CMD
1 0 sh -c exec sleep 1 & ps -Ho pid,ppid,cmd
7 1 sleep 1
8 1 ps -Ho pid,ppid,cmd
docker run --rm -it ubuntu:18.04 sh -c 'env sleep 1 & ps -Ho pid,ppid,cmd'
PID PPID CMD
1 0 sh -c env sleep 1 & ps -Ho pid,ppid,cmd
7 1 sleep 1
8 1 ps -Ho pid,ppid,cmd
问题
我看到很多人在使用exec env ...
,但我认为没有exec
必要,因为env
不会像exec
.
有没有我们需要使用的用例来exec env
代替env
?
env
(可能)本身不会分叉,只是用它所做的程序替换自己。但这与父 shell 分叉不同env
,或者只是用env
.例如比较这两个:
使用
exec
,外壳本身被替换,并且以下内容echo
不运行。当然,你有
exec env ... &
。使用&
,shell 无论如何都会分叉以启动后台进程,并且它可能不会再次分叉以在后台任务中运行单个命令。至少 Bash 优化了这样的情况,例如:如果后者不显示中间
bash
过程,则行为与存在中间过程相同exec
。(-/bin/bash
是我的交互式外壳。)Bash 只对一个单独的命令执行此操作,如果有多个命令,shell 将等待最后一个退出。使用
exec
那里会有所作为:&
,这与相同exec ps
:但是使用复合块,我们也可以看到后台 shell 进程:
你没有提供这些人的任何具体来源
exec env
,所以我们不知道他们的确切情况。但是你会使用exec env
相同的方式exec anyprogram
:如果你想用其他进程替换 shell。例如这个模拟示例:那里用启动的
exec
程序替换脚本,这样shell就不会无用地留在内存中。此外,如果脚本只有一个中介来启动程序,那么执行 anexec
将使 PID 保持不变,这使得父级(脚本和程序的)更容易监控其子级。