我正在尝试读取 proc.stdout.readline 中的每一行并通过网络发送这些行,例如:
data = b''
for line in iter(proc.stdout.readline, ''):
data += line
clientsocket.send(data)
当我运行这段代码时,我似乎陷入了无限循环,无法逃脱到该行:
clientsocket.send(data)
有没有更高效的读取数据的方法?我也尝试过使用 while 循环并打破“if not line”:
data = b''
while True:
line += proc.stdout.readline()
data += line
if not line:
break
clientsocket.send(data)
这似乎也产生相同的结果。有没有更有效的方法从 proc.stdout.readline 读取所有数据?
我也遇到过同样的问题。奇怪的是,在 Python 2.7 中,它没有收敛问题,而且实际上停止了迭代。 在调试期间(在 Python 3.5 中),我注意到所有真正的行都以
'\n'
字符返回,而原本不应该到达的行则作为空字符串返回,即 ''
。所以,我只是添加了一个 if 子句来检查 ''
,如果为正则中断循环。lines = []
for _line in iter(process.stdout.readline, b''):
if _line == '':
break
lines.append(_line)
可能值得一提的一件事是,我在
universal_newlines=True
调用时使用了 subprocess.Popen(..)
参数。
语句:
iter(proc.stdout.readline, "")
将执行阻塞读取,直到收到 EOF。
如果你想阅读所有行,那么你可以这样做:
data = b''
data = b"".join(proc.stdout.readlines())
除了让
proc
更快地生产线条之外,没有其他解决方案。
如果需要,您可以超时读取行(即您可以等待读取选定数量的字符,或者如果未读取该数量的字符则超时)。
这些答案可以在这里找到:
我还在一些
iter(p.stdout.readline, b'')
任务中遇到了subprocess.Popen
永远卡住的问题。
那些突破
iter
的技巧(123)都不起作用。
我最终发现这是因为
stderr
也有输出但从未被读取,导致无限等待和挂起。
要解决这个问题,您需要阅读这两本。代码片段来自 Dev Aggarwal 和 Deepak Yadav 此处:
import sys
import selectors
def popen_reader(p: subprocess.Popen) -> tuple:
sel = selectors.DefaultSelector()
sel.register(p.stdout, selectors.EVENT_READ)
sel.register(p.stderr, selectors.EVENT_READ)
done = False
while not done:
for key, _ in sel.select():
data = key.fileobj.read1().decode() # noqa
# ignore "Cannot find reference 'read1' in 'int | HasFileno'"
if not data:
done = True
break
if key.fileobj is p.stdout:
print(data, end="")
else:
print(data, end="", file=sys.stderr)
return p.wait()