Python-多進程共享數據2

多個進程之間共享list、dict等類型,可以使用multiprocessing模塊裏的Manager方法,由Manager()返回的管理器對象控制着一個服務器進程,該進程持有Python對象,並允許其他進程使用代理對其進行操作,管理器對象支持的類型有list, dict, Namespace, Lock, RLock, Semaphore, BoundedSemaphore, Condition, Event, Queue, Value and Array

共享列表和字典示例代碼:

from multiprocessing import Process, Manager

def f(d, l):
    d[1] = '1'
    d['2'] = 2
    d[0.25] = None
    l.reverse()

if __name__ == '__main__':
    with Manager() as manager:
        d = manager.dict()
        l = manager.list(range(10))

        p = Process(target=f, args=(d, l))
        p.start()
        p.join()

        print(d)
        print(l)

 輸出:

{0.25: None, 1: '1', '2': 2}
[9, 8, 7, 6, 5, 4, 3, 2, 1, 0]

注意,如果想要使用嵌套的列表和字典,嵌套的列表和字典必須都使用Manager.list和Manager.dict返回的對象,否則內層的列表和變量不會被修改。如下是錯誤代碼

from multiprocessing import Process, Manager

def f(d):
    d['numbers'].reverse()

if __name__ == '__main__':
    with Manager() as manager:
        d = manager.dict()
        d['numbers']=list(range(10))

        p = Process(target=f, args=(d,))
        p.start()
        p.join()

        print(d)

輸出

{'numbers': [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]}

可以看到數據並沒有改變,正確寫法如下:

 

from multiprocessing import Process, Manager

def f(d):
    d['numbers'].reverse()

if __name__ == '__main__':
    with Manager() as manager:
        d = manager.dict()
        d['numbers']=manager.list(range(10))

        p = Process(target=f, args=(d,))
        p.start()
        p.join()
        
        print(d)
        print(d['numbers'])

輸出如下:

{'numbers': <ListProxy object, typeid 'list' at 0x256d569f160>}
[9, 8, 7, 6, 5, 4, 3, 2, 1, 0]

 結果正確。

參考:

1.https://docs.python.org/3.7/library/multiprocessing.html#sharing-state-between-processes

 

 
 
 
 
 
發佈了18 篇原創文章 · 獲贊 7 · 訪問量 7230
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章