为了账号安全,请及时绑定邮箱和手机立即绑定

终止时未写入 Python3 中多处理进程的实例变量

终止时未写入 Python3 中多处理进程的实例变量

小怪兽爱吃肉 2021-08-14 15:33:06
我在编写在进程终止期间保存一些值的逻辑时遇到的一件令人惊讶的事情对我来说有点奇怪。编写一个玩具示例程序来显示问题。import multiprocessingimport timeclass A(multiprocessing.Process):    def __init__(self):        self.till = 0        super(A, self).__init__()    def run(self):        i = 0        while True:            print(i)            i += 1            self.till = i            time.sleep(1)    def terminate(self):        print("Terminating : {}".format(self.till))        super(A, self).terminate()if __name__ == "__main__":    obj = A()    obj.start()    time.sleep(5)    obj.terminate()上述程序的输出是 -01234Terminating : 0为什么终止()不打印出 4?我缺少什么吗?
查看完整描述

2 回答

?
拉风的咖菲猫

TA贡献1995条经验 获得超2个赞

你所做的实际上是在主进程上运行 terminate,看这段代码:


class A(multiprocessing.Process):

def __init__(self):

    self.till = 0

    super(A, self).__init__()


def run(self):

    i = 0

    print(os.getpid())

    while True:

        print(i)

        i += 1

        self.till = i

        time.sleep(1)


def terminate(self):

    print("Terminating : {}".format(self.till))

    print(os.getpid())

    super(A, self).terminate()


if __name__ == "__main__":

    print("parent pid:")

    print(os.getpid())

    print("child pid:")

    obj = A()

    obj.start()

    time.sleep(3)

    obj.terminate()

将导致输出:


parent pid:

12111

child pid:

12222

0

1

2

Terminating : 0

12111

在终止时,您实际上是发送SIGTERM到子进程,它是从父进程完成的,因此内存是父进程的,没有增量self.till


查看完整回答
反对 回复 2021-08-14
?
白猪掌柜的

TA贡献1893条经验 获得超10个赞

init和 terminate 方法在主进程上运行,因此子进程为您的终止函数打印 0。Run 方法仅在子进程中递增。您可以通过在 python 中使用 os.getpid() 方法来确认这一点。

编辑:这个问题可能只发生在 Windows 中,因为它没有像 Linux/Unix 系统那样的 fork() 系统调用。Windows从头启动整个模块以达到效果。


查看完整回答
反对 回复 2021-08-14
  • 2 回答
  • 0 关注
  • 149 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信