Python:迭代地在大数组上并行化操作

时间:2015-05-24 06:42:18

标签: python parallel-processing multiprocessing

我正在尝试并行化大阵列上的操作。我在下面的代码片段中总结了我的方法。由于大数组上的操作成本很高,在100个进程中,我想在每次迭代时并行化4(即n_cpus)。迭代完成后,将完成一些垃圾收集,并开始下一次迭代。主循环执行第一次迭代并终止。如果某个并行处理专家可以指出我如何纠正我的代码以实现所需的任务,我将很高兴。

from multiprocessing import Process

def train_model(model, big_array, i):
    model = do_operations_on(big_array)

# edit: this part is within a class
n_processes = 100
n_cpus = 4
models = [None for _ in range(n_processes)]
n_iterations = n_processes / n_cpus
for it in range(n_iterations):
    procs = [Process(target=train_model, \
        args=(models[it*n_cpus+i], big_array, i)) for i in range(n_cpus)]

    for p in procs: p.start()
    for p in procs: p.join()

1 个答案:

答案 0 :(得分:1)

除了一些问题外,你的想法似乎基本没问题:

  • 正如RaJa所指出的那样,您应该使用队列而不是使用共享状态传递内容

  • 我认为你在multiprocessing.Process的使用在这里是不必要的低级别;您应该使用multiprocessing.Pool,这也会更有效率,因为您可以重复使用这些流程(而不是保持设置并将其拆除)。

  • 由于train_model忽略modeli,您的代码会有一些混淆,只会覆盖模型。

所以,在下面的代码中,我假设你有类似

的东西
def train_model(specs, big_array):
    return ...

获取一些spec细节和数据,并返回为这些细节构建的模型。

我还假设在下面你有一些数组specifics包含你想要尝试的所有细节(并且它在cpus的数量上是可分的,这并不难以摆脱)。

最后,我认为重点是建立所有模型的列表models

您的代码变为:

from multiprocessing import Pool

n_cpus = 4
n_iterations = len(specifics) / n_cpus
models = []
p = multiprocessing.Pool(n_cpus)
for it in range(n_iterations):
    cur_specs = specifics[it * n_cpus: (it + 1) * n_cpu]
    cur_models = p.map(lambda specs: train_model(specs, big_array), cur_specs)
    models.extend(cur_models)
    # Cleanup here