一尘不染

python:在多个实例上并行调用方法

python

我试图在多个实例并行引用同一方法,其中实例引用同一对象。

很抱歉造成这种混淆。

具体来说,我想将以下for循环更改为并行执行:

for i in range(len(instances)):#instances is a list of instances
   instances[i].do_some_computation_over_a_dataset()

可能吗?

未来读者注意事项:

上面的代码不是迭代Python中实例集合的方法。这是一种以顺序(即非并行)方式进行迭代的方法:

for i in instances:
    i.do_some_computation_over_a_dataset()

阅读 349

收藏
2021-01-20

共1个答案

一尘不染

好的,让我们一起做。首先是代码(multiprocessing
docs
):

In [1]: from multiprocessing import Process

In [2]: def f():
   ...:     print(1)
   ...:     for i in range(100):
   ...:         # do something
   ...:         pass
   ...:

In [3]: p1 = Process(target=f)

In [4]: p1.start()

1
In [5]: p2 = Process(target=f)

In [6]: p2.start()

1
In [7]: import time

In [8]: def f():
   ...:     for i in range(100):
   ...:         print(i)
   ...:         # do something
   ...:         time.sleep(1)
   ...:         pass
   ...:
In [9]: p1 = Process(target=f)
In [9]: p1 = Process(target=f)

In [10]: p1.start()

0
In [11]: p2 1
= Process(target=f)2
3
4
5
In [11]: p2 = Process(target=f)

In [12]: 6
p2.7
start8
In [12]: p2.start()

0
In [13]: 9

这是如何并行调用函数的示例。从In [10]: p1.start()你所看到的,因为程序P1并联运行时,我们运行程序P2的输出被搞乱。

使用Python脚本运行程序时,您要确保脚本仅在所有程序成功执行后才结束。你可以这样做

def multi_process(instance_params, *funcs):
   process = []
   for f in funcs:
       prog = Process(target=f, args=instance_params)
       prog.start()
       process.append(prog)
   for p in process:
       p.join()

multi_process(params, f, f)

由于GIL,Python没有C
++或Java之类的多线程支持。在这里阅读。尽管如果您的程序能够执行更多的I
/ O操作,然后执行CPU密集型任务,那么您可以使用多线程。为了执行CPU密集型任务,建议进行多处理。

@ytutow在评论中询问了 工作人员流程
之间的区别是什么。从Pymotw

池类可用于管理固定数量的工人,以用于简单的情况,在这些情况下,可以分解要完成的工作并在工人之间独立分配。

收集作业的返回值并作为列表返回。

池参数包括进程数和启动任务进程时要运行的函数(每个子进程调用一次)。

您可以将Pool用作:

def your_instance_method(instance):
   instances.do_some_computation_over_a_dataset()

with Pool(3) as p:
    instances = [insatnce_1, instance_2, instance_3]
    print(p.map(your_instance_method, instances))

关于正确的工人数,一般建议使用2 * cpu_cores工人数。

2021-01-20