Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/347.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 如何在subprocess.Popen之后进行清理?_Python_Subprocess_Pipe_Popen_Lsof - Fatal编程技术网

Python 如何在subprocess.Popen之后进行清理?

Python 如何在subprocess.Popen之后进行清理?,python,subprocess,pipe,popen,lsof,Python,Subprocess,Pipe,Popen,Lsof,我有一个长时间运行的python脚本和一个perl worker子进程。数据通过其stdin和stdout进出子进程。必须定期重新启动子级 不幸的是,运行一段时间后,它的文件用完了(“打开的文件太多”)。lsof显示了许多剩余的开放管道 什么是正确的方法来清理后的Popen'd的过程?以下是我现在正在做的: def start_helper(self): # spawn perl helper cwd = os.path.dirname(__file__) if not

我有一个长时间运行的python脚本和一个perl worker子进程。数据通过其stdin和stdout进出子进程。必须定期重新启动子级

不幸的是,运行一段时间后,它的文件用完了(“打开的文件太多”)。lsof显示了许多剩余的开放管道

什么是正确的方法来清理后的Popen'd的过程?以下是我现在正在做的:

def start_helper(self):
    # spawn perl helper
    cwd = os.path.dirname(__file__)
    if not cwd:
        cwd = '.'

    self.subp = subprocess.Popen(['perl', 'theperlthing.pl'], shell=False, cwd=cwd,
                                 stdin=subprocess.PIPE, stdout=subprocess.PIPE,
                                 bufsize=1, env=perl_env)

def restart_helper(self):
    # clean up
    if self.subp.stdin:
        self.subp.stdin.close()
    if self.subp.stdout:
        self.subp.stdout.close()
    if self.subp.stderr:
        self.subp.stderr.close()

    # kill
    try:
        self.subp.kill()
    except OSError:
        # can't kill a dead proc
        pass
    self.subp.wait() # ?

    self.start_helper()

快速实验表明,
x=open(“/etc/motd”);x=1
会在其自身之后进行清理,并且不会留下任何打开的文件描述符。如果删除对
subprocess.Popen的最后一个引用,管道似乎会粘住。您是否可以在不明确关闭和停止旧的帮助程序的情况下重新调用
start\u helper()

def restart_helper(self):
    # kill the process if open
    try:
        self.subp.kill()
    except OSError:
        # can't kill a dead proc
        pass

    self.start_helper()
    # the wait comes after you opened the process
    # if you want to know how the process ended you can add
    # > if self.subp.wait() != 0:
    # usually a process that exits with 0 had no errors
    self.subp.wait()

据我所知,所有文件对象都将在popen进程终止之前关闭。

popen.kill
(或
popen.terminate
)是您最好的选择。当您终止它时,除了已经死了之外,它还会因为其他原因引发操作系统错误吗?
子流程中有一个稍微不相关的错误,但它可能会对
\u cleanup()
使用
close\u fds=True
(py3k上的默认值)有所帮助,如果您不在Windowsbtw上,在某些系统上,打开文件的数量限制非常小。wait()是不让子进程和打开管道掉队的关键。我认为这最终是正确的。