gpt4 book ai didi

使用 os.pipe 和 os.fork() 问题的 Python 程序

转载 作者:太空狗 更新时间:2023-10-29 18:28:28 28 4
gpt4 key购买 nike

我最近需要编写一个脚本来执行 os.fork() 以拆分为两个进程。子进程成为服务器进程,并使用由 os.pipe() 创建的管道将数据传回父进程。像往常一样,子项关闭管道的 'r' 端,父项关闭管道的 'w' 端。我使用 os.fdopen 将 pipe() 的返回值转换为文件对象。

我遇到的问题是:进程成功 fork ,子进程成为服务器。一切正常, child 尽职尽责地将数据写入管道的开放 'w' 端。不幸的是,管道的父端做了两件奇怪的事情:
A) 它阻塞在管道的 'r' 端的 read() 操作。
其次,它无法读取任何放在管道上的数据,除非 'w' 端完全关闭。

我立即认为缓冲是问题所在,并添加了 pipe.flush() 调用,但这些都没有帮助。

任何人都可以阐明为什么在写入端完全关闭之前数据不会出现吗?是否有使 read() 调用非阻塞的策略?

这是我的第一个 fork 或使用管道的 Python 程序,如果我犯了一个简单的错误,请原谅我。

最佳答案

您是在未指定大小的情况下使用 read(),还是将管道视为迭代器(for line in f)?如果是这样,那可能是问题的根源 - read() 被定义为在返回之前一直读取到文件末尾,而不是只读取可供读取的内容。这意味着它将阻塞,直到 child 调用 close()。

在链接到的示例代码中,这是可以的 - 父级以阻塞方式运行,并且仅将子级用于隔离目的。如果你想继续,那么要么像你发布的代码那样使用非阻塞 IO(但要准备好处理半完整的数据),要么分 block 读取(例如 r.read(size) 或 r.readline() ) 只会在读取特定大小/行之前阻塞。 (您仍然需要对 child 调用 flush)

看起来将管道视为迭代器也在使用一些进一步的缓冲区,因为“for line in r:”如果您需要立即显示每一行,可能不会给您想要的结果消费。可以禁用它,但仅将 fdopen 中的缓冲区大小指定为 0 似乎不够。

下面是一些应该有效的示例代码:

import os, sys, time

r,w=os.pipe()
r,w=os.fdopen(r,'r',0), os.fdopen(w,'w',0)

pid = os.fork()
if pid: # Parent
w.close()
while 1:
data=r.readline()
if not data: break
print "parent read: " + data.strip()
else: # Child
r.close()
for i in range(10):
print >>w, "line %s" % i
w.flush()
time.sleep(1)

关于使用 os.pipe 和 os.fork() 问题的 Python 程序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/871447/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com