我正在使用Popen执行shell脚本。我也使用 stdout = PIPE 来捕获输出。代码是
pipe = Popen('acbd.sh', shell=True, stdout = PIPE)
while pipe.poll() is None:
time.sleep(0.5)
text = pipe.communicate()[0]
if pipe.returncode == 0:
print "File executed"
根据使用 stdout = PIPE 的民意调查的文档可能会导致死锁。此外, communication()可用于解决此问题。我在这里使用了communication()。
我的代码是否也会因为沟通导致死锁,或者我使用沟通使用错误了吗?
另外我在subprocess.check_output中有一个替代,但我更喜欢使用Popen并用相同的方式记录输出。
答案 0 :(得分:2)
是的,你可以死锁,因为这两行:
while pipe.poll() is None:
time.sleep(0.5)
带他们出去;这里没有必要。 communicate()
将等待子进程关闭其FD(如退出时那样);当你自己添加一个循环,并且直到该循环完成后才读取,那么你的程序可能会被无限期地卡住,试图写出在communicate()
导致之前无法写入的内容管道的另一边开始阅读。
作为背景:write()
调用的POSIX规范不保证在阻塞之前可以写入FIFO的数据量,或者这个数据量是否一致即使在给定的系统中 - 因此,安全的事情是假设对FIFO的任何写入总是允许阻止,除非读者主动消耗该数据。