如何在python多处理中实现reduce操作?

时间:2017-09-20 06:21:04

标签: python multithreading parallel-processing multiprocessing reduce

我是OpenMP和C ++的专家并行程序员。现在我试图理解python和multiprocessing库中的并行性。

特别是,我正在尝试并行化这个简单的代码,它会随机增加一个数组100次:

from random import randint
import multiprocessing as mp
import numpy as np

def random_add(x):
    x[randint(0,len(x)-1)]  += 1

if __name__ == "__main__":
    print("Serial")
    x = np.zeros(8)
    for i in range(100):
        random_add(x)
    print(x)

    print("Parallel")
    x = np.zeros(8)    
    processes = [mp.Process(target = random_add, args=(x,)) for i in range(100)]
    for p in processes:
        p.start()
    print(x)

但是,这是以下输出:

Serial
[  9.  18.  11.  15.  16.   8.  10.  13.]
Parallel
[ 0.  0.  0.  0.  0.  0.  0.  0.]

为什么会这样?好吧,我想我有一个解释:因为我们处于多处理(而不是多线程),每个进程都是他自己的内存部分,即每个生成的进程都有自己的x,它被销毁一次{ {1}}已终止。结论是,主程序中的random_add(x)永远不会真正更新。

这是对的吗?如果是这样,我该如何解决这个问题呢?简而言之,我需要一个全局reduce操作,它对所有x调用的结果求和,得到相同的串行版本结果。

1 个答案:

答案 0 :(得分:2)

您应该在您的情况下使用共享内存对象:

from random import randint
import multiprocessing as mp

def random_add(x):
    x[randint(0,len(x)-1)]  += 1

if __name__ == "__main__":
    print("Serial")
    x = [0]*8
    for i in range(100):
        random_add(x)
    print(x)

    print("Parallel")
    x = mp.Array('i', range(8))
    processes = [mp.Process(target = random_add, args=(x,)) for i in range(100)]
    for p in processes:
        p.start()
    print(x[:])

为了清晰代码,我已将numpy数组更改为序数列表