python父进程调用子进程_Python2.7下,调用subprocess启动子进程,读取子进程标准输出若干问题...
1:如果調用的子進程也是一個python腳本,則subprocess.Popen中的bufsize=1無效果。也就是說,即使設置了bufsize=1表示進行行緩沖,子進程如果不顯示調用sys.stdout.flush,父進程依然會阻塞在readline上:
#testbuf.py
importsubprocess
cmd= "./testsub.sh"cmd2= ["python", "testsub.py"]
sp= subprocess.Popen(cmd2, bufsize = 1, stdout =subprocess.PIPE)whileTrue:
line=sp.stdout.readline()print 'read line is', lineif not line: break
testsub.py代碼如下:
importtimeimportsysfor i in range(100000):print 'hello, world', i#sys.stdout.flush()
time.sleep(1)
執行testbuf.py腳本,該腳本將會阻塞在sp.stdout.readline()上,除非將子進程testsub殺掉,否則,該腳本將會長時間阻塞在這條語句上。
如果將testsub.py中的sys.stdout.flush()前注釋去掉,則父進程可以得到正常的輸出。
如果執行的是shell腳本testsub.sh,則沒有這種問題,該腳本代碼如下:
#!/bin/bashfor((i=1;i<=10000000;i++));do
echo“hello, world”, $isleep 1
done
2:如果子進程是一個長時間運行的程序,而父進程想以行為單位實時讀取子進程的輸出,則父進程不能以for line in sp.stdout的形式讀取子進程輸出:
#testbuf.py
import subprocess
cmd= "./testsub.sh"cmd2= ["python", "testsub.py"]
sp= subprocess.Popen(cmd2, bufsize = 1, stdout =subprocess.PIPE)for line insp.stdout:
print'read line is', lineif not line: break
這種情況下,進程阻塞在for line in sp.stdout上。這實際上是python2的一個bug:
https://bugs.python.org/issue3907
https://stackoverflow.com/questions/2804543/read-subprocess-stdout-line-by-line
https://ubuntuforums.org/showthread.php?t=916518
這個bug在python3中據說解決了,但是在python2下,還是不可以用for line in sp.stdout這種形式。可以使用readline:
for line in iter(proc.stdout.readline,''):
print line
3:如果子進程有大量輸出,而父進程調用subprocess.Popen時又設置了stdout = subprocess.PIPE,并且沒有及時讀取stdout中的內容,則一旦緩沖區滿了(緩沖區默認大小為65535),則子進程會在寫入標準輸出時hang住。
總結
以上是生活随笔為你收集整理的python父进程调用子进程_Python2.7下,调用subprocess启动子进程,读取子进程标准输出若干问题...的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 末日生存游戏 《大灾变:黑暗之日》上架
- 下一篇: 关于Struts1框架的简介与入门(SS