所以我试图将HandBrakeCLI的输出捕获为Python子进程。这不是stderr的问题,因为每次更新都会在类似文件的管道中创建一个新行。但是,使用stdout,HandBrakeCLI进行就地更新,我很难捕获它们。我甚至不知道调用就地更新的内容,这使得查找相关提示有点棘手。
到目前为止,我提出的唯一解决方案是将stdout写入实际文件并从中读取,但我宁愿以理智的方式(在内存中)这样做。
COMMAND = ['HandBrakeCLI', '-v', '-i', 'in.m4v', '-o', 'out.m4v', '-Z', 'Normal']
outfile = open('output.txt', 'w')
proc = subprocess.Popen(COMMAND, stdout=outfile, stderr=subprocess.PIPE)
infile = open('output.txt', 'r')
while proc.poll() is None:
print infile.read()
infile.seek(0)
这样可行,但必须有更好的方法。当尝试使用communic()或只是简单的proc.stdout.read()时,我什么都没得到。
我做错了什么?谢谢!
根据@wim建议我检查了看看HandBrakeCLI提供的原始输出是什么,它看起来像这样:
\rEncoding: task 1 of 1, 0.15 %
处理以\ r?
为前缀的标准输出的最佳方法是什么?答案 0 :(得分:5)
我认为上面关于使用universal_newlines = True的评论会有效。
这是一个示例就地编写器,名为“inplace_output.py”
import sys
import time
def main():
for k in range(5):
print "{0:03d}\r".format(k),
sys.stdout.flush()
time.sleep(1)
if __name__ == "__main__":
main()
你可以运行它,并且每次覆盖之前的输出时都会看到000,然后是001等。
这是一个脚本,它将上述作为子进程运行,并逐行读取其输出:
import subprocess
cmd = ['python', 'inplace_output.py']
proc = subprocess.Popen(cmd, stdout=subprocess.PIPE, universal_newlines=True)
while True:
out = proc.stdout.readline()
print repr(out)
if len(out) == 0:
break
如果想在子进程程序终止时立即收集所有输出,可以用,例如,
替换while循环out, err = proc.communicate()
lines = out.splitlines()
其中任何一个都适合你吗?