您可以使用子流程myprocess.stdin.write()
并myprocess.stdout.read()
与之进行通信,您只需要注意确保正确处理缓冲,以防止调用阻塞即可。
如果子流程的输出定义明确,则应该能够使用行缓冲和可靠地与其进行通信myprocess.stdout.readline()
。
这是一个例子:
>>> p = subprocess.Popen(['cat'], bufsize=1, stdin=subprocess.PIPE, stdout=subprocess.PIPE)
>>> p.stdin.write('hello world\n')
>>> p.stdout.readline()
'hello world\n'
>>> p.stdout.readline() # THIS CALL WILL BLOCK
对于Unix,此方法的另一种选择是将文件句柄置于非阻塞模式,这将允许您调用类似的函数myprocess.stdout.read()
,并让其返回数据(如果有的话),或者引发IOError
如果没有任何数据:
>>> p = subprocess.Popen(['cat'], stdin=subprocess.PIPE, stdout=subprocess.PIPE)
>>> import fcntl, os
>>> fcntl.fcntl(p.stdout.fileno(), fcntl.F_SETFL, os.O_NONBLOCK)
0
>>> p.stdout.read() # raises an exception instead of blocking
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
IOError: [Errno 11] Resource temporarily unavailable
这将允许您执行以下操作:
fcntl.fcntl(p.stdout.fileno(), fcntl.F_SETFL, os.O_NONBLOCK)
for text in textcollection:
myprocess.stdin.write(text + '\n')
while True:
myoutputtext = ''
try:
myoutputtext += myprocess.stdout.read()
except IOError:
pass
if validate_output(myoutputtext):
break
time.sleep(.1) # short sleep before attempting another read
在此示例中,validate_output()
您需要编写一个函数,True
如果到目前为止收到的数据是您希望获得的所有输出,则该函数将返回。