为什么subprocess.Popen.wait使用繁忙循环?
问题描述:
如文档here,Popen.wait确实忙于等待。我相信一些操作系统有系统调用来等待进程结束,而不需要繁忙的循环。为什么不使用这种机制?为什么subprocess.Popen.wait使用繁忙循环?
答
我不完全是积极的。我不认为有一种方法可以让waitpid或相当于一个完全非侵入性的同步超时。另外,我认为一些Unices对于waitpid如何使用信号玩法有不同的规则。
评论说他们偷了Thread.wait
的循环,threading.py中的注释表明它用于响应。
答
from subprocess import Popen, PIPE
handle = Popen('ping -n 100 www.google.se', shell=True, stdout=PIPE)
while handle.poll() is None: # <-- Equivilant of .wait()
print(handle.stdout.readline())
等待是.poll(),它基本上没有,除非你手动使用.poll()在保持循环,您可以在此过程中计算的东西同样的事情速记功能。
通常它用于转储出标准输出/标准错误的东西(如果你不能阻止应用程序或引发异常)。
还使用shell
是有风险的,但它在学习和测试时可以节省很多头痛。
真正不会阻止在所有东西(即使上述方法“块”下一行中的代码)的唯一方式是向utelize线程:
from threading import *
from subprocess import Popen, PIPE
class worker(Thread):
def __init__(self, command):
Thread.__init__(self)
self.handle = Popen(command, shell=True, stdout=PIPE)
self.start()
def run(self):
while self.handle.poll() is None:
print('Thread-output',self.handle.stdout.readline()) # Note, you might loose the last output.. just saying.
print('I\'m a panda..')
worker('ping -n 100 www.google.se')
print('And i work really well simultaneously...')
有用尖端调试时:
from subprocess import Popen, PIPE, STDOUT
handle = Popen('ping -n 100 www.google.se', shell=True, stdout=PIPE, stderr=PIPE)
# You need to flush the output buffers:
handle.stderr.readline()
handle.stdout.readline()
# or
handle = Popen('ping -n 100 www.google.se', shell=True, stdout=PIPE, stderr=STDOUT)
handle.stdout.readline() # Does both stdout+stderr at the same time, saves you a line.
# and always close your open filehandles.
handle.stdout.close()
handle.stderr.close() # If you've separated both.
关于你的操作系统问题
我想你可能指的是系统服务或守护进程?
这些类型的“进程”,你描述他们被指定为阻塞或非阻塞(这是你正在寻找的术语)。这些进程的每个init脚本的开发者决定进程是否应该被阻塞直到完成(或达到超时)或进程应该分入后台。
可能被阻止的事情是OpenLDAP或内部邮件传输器,而其他进程(例如OpenVPN或Apache)可能会分入后台,让系统启用以继续它的启动顺序。
不必要地运行一个shell并不能挽救头痛,它会创建它们(并且更糟!) – 2014-11-05 18:55:50
@MikeGraham如果你不知道去除什么东西,它确实如此。因为任何unix shell都可以做到这一点,所以它的行为会更好。我意识到不使用这是理想的,但对于新的unix用户来说,像任何其他具有环境变量的unix shell一样运行的默认行为更容易。 – Torxed 2014-11-05 20:28:33
@Torxed根据[this](https://*.com/questions/26750541/how-does-time-wait-for-a-process-that-it-is-timing),我们可以阻止呼叫而不需要在Unix上忙于循环。那么为什么不在Popen.wait上实现呢,因为忙于等待进程完成浪费CPU资源? – ggg 2014-11-06 01:00:37