Python Multiprocessing - 修改共享字典中的值

标签 python dictionary python-multiprocessing

我正在做一个项目,我将来自一个进程的数据解析为 python 字典,然后由另一个 python 进程读取,创建不同的数据 View 。解析的数据来自 worker1 进程处理的传感器。

到目前为止,我可以使用共享字典创建两个进程,并且我最终可以毫无问题地向它添加值。但是,当我想修改现有值时,我碰壁了。我已经阅读了数小时的“许多”答案并尝试了解决方案,例如创建一个包含 key 的新对象。例如。 x = d["键"][1];x = '新值'。只是行不通。我在 python 3.6 中运行代码,但问题在 2.7 中似乎类似。这是简化版本的代码:

#!/usr/bin/python3
import subprocess,time
from multiprocessing import Process, Manager

def worker1(d):
    d["key"] = []    #Creating empty dict item
    d["key"]+=["hellostack"] #Adding first value
    d["key"]+=[1]    #Adding second value
    print ("from worker1:",d)
    d["key"][1]+=2 #<<<< ISSUE HERE - Modifying second value does nothing
    print ("Now value should be upped!..",d)

def worker2(d):
    while True:
        time.sleep(1)
        print ("from worker 2:",d)

manager = Manager()
d = manager.dict()

worker1 = Process(target=worker1, args=(d,))
worker2 = Process(target=worker2, args=(d,))
worker1.start()
worker2.start()
worker1.join()
worker2.join()

我得到的输出是:

from worker1: {'key': ['hellostack', 1]}
Now value should be upped!.. {'key': ['hellostack', 1]}
from worker 2: {'key': ['hellostack', 1]}

有人吗? :o)

编辑:可能的重复,不关注两个单独的进程,也不谈论内部有列表的字典。然而,诚然非常相似,实际上答案让我找到了答案。所以我将暂时保留这一点。

最佳答案

这是可变值和多处理在进程之间同步数据的方式的副作用。

您从 multiprocessing.Manager 获得的 dict 不是某种共享内存。它通过消息显式同步到子流程,当经理注意到修改时!

它如何注意到修改?

简单:只需使用将内容同步到其他进程的代理覆盖 dict 的所有修改方法。您可以看到代理方法列表 here在 python 源代码中。

让我们逐行查看您的示例工作人员:

d["key"] = []    #Creating empty dict item

好的,调用了 __setitem__,代理注意到了变化。

d["key"]+=["hellostack"] #Adding first value

这里几乎一样,先是__getitem__,不同步,然后是__setitem__设置新值。

d["key"]+=[1]    #Adding second value

与上一个相同,先添加获取项,然后再设置。

d["key"][1]+=2 #<<<< ISSUE HERE - Modifying second value does nothing

好的,__getitem__ 获取列表(不是 ListProxy!),然后修改它就地,列表是可变值。 DictProxy 永远不会看到 __setitem__ 调用,也永远不会同步任何东西。所以 worker2 永远看不到这种变化。

关于Python Multiprocessing - 修改共享字典中的值,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45869869/

相关文章:

python - 将数据附加到python字典

android - Python 和 Android Fastboot 的输出

Python 在多列中查找重复项

c# - 如何在 C# 字典中找到具有最高值的键?

python - 多处理是否在这种情况下复制对象?

python - 显示经过身份验证的用户使用模型管理器创建的条目

c# - mapwingis 形状没有添加到 shapefile

c++ - 如何在 unordered_map 中设置值并确定是否添加了新键

python - 对 Pandas 中的行进行多重处理以替换为 REGEX

python - 在多处理进程之间将opencv视频帧共享为Numpy数组的正确方法