nohup和&符有什么区别


242

两者nohup myprocess.out &myprocess.out &将myprocess.out设置为在后台运行。关闭终端后,该过程仍在运行。它们之间有什么区别?


您正在使用什么外壳?跨越炮弹的行为变化
shx2

1
重击。我知道为什么现在要根据@nemo的答案。
Yarkee

@Yarkee如果答案适合您的问题,请将该问题标记为已接受(答案投票下方的复选框),这样就不会悬而未决。您应该对所有问题都这样做:)
nemo 2013年

1
shutdown应避免使用具有特定Linux含义的术语。并用代替exit
Patrizio Bertoni 2014年

Answers:


316

nohup捕获挂断信号(请参阅参考资料man 7 signal),而“&”号不捕获(除非shell以这种方式配置或根本不发送SIGHUP)。

通常,当使用此命令运行&并退出Shell之后,Shell将以挂断信号(kill -SIGHUP <pid>)终止子命令。可以使用来防止这种情况nohup,因为它会捕获信号并忽略该信号,因此它永远不会到达实际应用程序。

如果您使用的是bash,则可以使用命令shopt | grep hupon来查找shell是否将SIGHUP发送到其子进程。如果关闭,进程将不会终止,这对您来说似乎就是这种情况。有关bash如何终止应用程序的更多信息,请参见此处

在有些情况下的情况下nohup,当这个过程中你开始重新连接不起作用,例如SIGHUP信号,因为它是如此这里


可能值得注意的是,它&确实会导致子命令未接收到某些信号(例如SIGINT)。nohup本质上增加SIGHUP了未传播信号的列表。
studgeek

46

myprocess.out &将使用子外壳程序在后台运行该过程。如果当前外壳程序终止(例如通过注销),则所有子外壳程序也会终止,因此后台进程也将终止。的nohup的命令忽略HUP信号,因此,即使当前壳被终止时,子外壳和myprocess.out将继续在后台运行。另一个区别是,&仅此一项不会重定向stdout / stderr,因此,如果有任何输出或错误,则会在终端上显示这些输出或错误。另一方面,nohup将stdout / stderr重定向到nohup.outor $HOME/nohup.out


6
我运行myprocess.out &并退出外壳。但是,当我ps aux | grep myprocess.out在其他shell中使用时,仍然可以找到“ myprocess.out”。这意味着该进程仍在运行,不会被终止。
Yarkee

1
@amit_g在杀死父shell kill -9时不会出现SIGHUP,因为这将要求父shell处理SIGKILL,而这不能。
nemo 2013年

2
支票购物 grep hupon如其他答案中所述。
2013年

31

大多数时候,我们使用ssh登录到远程服务器。如果启动外壳程序脚本并注销,则该过程将被终止。Nohup帮助您即使在退出Shell后仍可在后台继续运行脚本。

Nohup command name &
eg: nohup sh script.sh &

Nohup捕获HUP信号。Nohup不会自动将作业放在后台。我们需要使用&明确告知


谢谢。没想到您会回答,但是事实真是太好了。它回答了我没有问的问题:D
Vaibhav Kaushal,2015年

26

使用&号(&)将在子进程(当前bash会话的子进程)中运行命令。但是,当您退出会话时,所有子进程将被杀死。

使用nohup +和号(&)会做同样的事情,除了在会话结束时,子进程的父进程将变为“ 1”(即“ init”进程),从而防止子进程被杀死。


7

如我错了请纠正我

  nohup myprocess.out &

nohup捕获挂断信号,这意味着当终端关闭时它将发送一个进程。

 myprocess.out &

进程可以运行,但是一旦关闭终端就会停止。

nohup myprocess.out

即使关闭了终端,进程也可以运行,但是您可以通过在终端中按ctrl+ 来停止进程zCrt+ z如果&存在则无法正常工作。


2

nohup命令是一种信号屏蔽实用程序,可以捕获挂断信号。其中,“&”号不会捕获挂断信号。当使用&运行命令并退出外壳程序时,外壳程序将以挂断信号终止子命令。这可以通过使用nohup来防止,因为它会捕获信号。Nohup命令接受挂断信号,该信号可以由内核发送给进程并阻止它们。当用户要启动长期运行的应用程序注销或关闭启动该进程的窗口时,Nohup命令很有用。这些操作通常都会提示内核挂断应用程序,但是nohup包装器将允许进程继续进行。使用&符将在当前bash会话的子进程和该子进程中运行命令。当您退出会话时,该进程的所有子进程将被杀死。“&”号与活动外壳的作业控制有关。这对于在后台的会话中运行进程很有用。


0

在许多情况下,环境之间的细微差异会刺伤您。这是我最近遇到的一个问题。这两个命令有什么区别?

1 ~ $ nohup myprocess.out &
2 ~ $ myprocess.out &

答案与平常相同-取决于情况。

nohup捕获挂断信号,而“&”号不捕获。

什么是挂断信号?

SIGHUP-在控制终端上检测到挂断或控制进程终止(值:1)。

通常,当使用&运行命令并随后退出外壳程序时,外壳程序将以挂断信号终止子命令(例如kill -SIGHUP $ PID)。使用nohup可以防止这种情况,因为它会捕获信号并将其忽略,从而使其永远无法到达实际应用程序。

很好,但是像在这种情况下,总是有“ buts”。当以完全不发送SIGHUP的方式配置外壳程序时,这两种启动方法之间没有区别。

如果您正在使用bash,则可以使用下面指定的命令来查找您的shell是否将SIGHUP发送到其子进程:

~ $ shopt | grep hupon

而且-在某些情况下nohup无法正常工作。例如,当您启动该过程时,将重新连接NOHUP信号(在应用程序代码级别在内部完成)。

在描述的情况下,当在定制服务启动脚本中调用第二个脚本而无需nohup命令来启动并启动正确的应用程序时,缺少差异困扰着我。

在一个Linux环境中,一切正常进行,在第二个环境中,第二个脚本退出后,应用程序立即退出(检测到这种情况,我花了更多时间,然后您可能会想到:stuck_out_tongue :)。

在将nohup作为启动方法添加到第二个脚本之后,即使脚本将退出并且该行为在两种环境下都变得一致,应用程序仍保持运行。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.