gpt4 book ai didi

python - 重新使用和关闭子流程对象的正确方法

转载 作者:太空狗 更新时间:2023-10-30 01:47:02 24 4
gpt4 key购买 nike

我在循环中有以下代码:

while true:
# Define shell_command
p1 = Popen(shell_command, shell=shell_type, stdout=PIPE, stderr=PIPE, preexec_fn=os.setsid)
result = p1.stdout.read();
# Define condition
if condition:
break;

其中 shell_command 类似于 ls(它只是打印内容)。

我在不同的地方读到过,我可以通过多种方式关闭/终止/退出 Popen 对象,例如:

p1.stdout.close()
p1.stdin.close()
p1.terminate
p1.kill

我的问题是:

  1. 使用完 subprocess 对象后,关闭它的正确方法是什么?
  2. 考虑到我的脚本的性质,有没有办法只打开一个subprocess 对象一次,然后用不同的 shell 命令重用它?这会比每次打开新的 subprocess 对象更有效吗?

更新

根据我是使用 p1.communicate() 还是 p1.stdout.read() 进行交互,我仍然对要遵循的步骤顺序感到困惑用我的过程。

根据我在答案和评论中的理解:

如果我使用 p1.communicate() 我不必担心释放资源,因为 communicate() 会等到进程完成,捕获输出并正确关闭 subprocess 对象

如果我遵循 p1.stdout.read() 路线(我认为这适合我的情况,因为 shell 命令只是应该打印东西)我应该按以下顺序调用:

  1. p1.wait()
  2. p1.stdout.read()
  3. p1.terminate()

是这样吗?

最佳答案

What is the proper way of closing a subprocess object once we are done using it?

stdout.close()stdin.close() 不会终止进程除非它在输入结束或写入错误。

.terminate().kill()两者都完成了工作,kill 在 POSIX 系统上有点“激烈”,因为 SIGKILL 被发送,应用程序不能忽略它。具体差异说明in this blog post , 例如。在 Windows 上,没有区别。

还有,记得给.wait()并在杀死进程后关闭管道以避免僵尸并强制释放资源。

一个经常遇到的特殊情况是从 STDIN 读取并将其结果写入 STDOUT 的进程,当遇到 EOF 时关闭自己。对于这些类型的程序,使用 subprocess.communicate 通常是明智的:

>>> p = Popen(["sort"], stdin=PIPE, stdout=PIPE)
>>> p.communicate("4\n3\n1")
('1\n3\n4\n', None)
>>> p.returncode
0

这也可以用于打印一些东西并在之后立即退出的程序:

>>> p = Popen(["ls", "/home/niklas/test"], stdin=PIPE, stdout=PIPE)
>>> p.communicate()
('file1\nfile2\n', None)
>>> p.returncode
0

Considering the nature of my script, is there a way to open a subprocess object only once and reuse it with different shell commands? Would that be more efficient in any way than opening new subprocess objects each time?

我认为 subprocess 模块不支持这一点,而且我看不到可以在此处共享哪些资源,因此我认为它不会给您带来显着优势。

关于python - 重新使用和关闭子流程对象的正确方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9585874/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com