如何解决Multiprocessing.Pool问题?

时间:2018-11-07 01:35:20

标签: python

我正在尝试按照以下python代码使用多重处理。

代码:

from multiprocessing import Pool

def fibo(n):
    if n == 0:
        return 0
    elif n == 1:
        return 1
    else:
        return fibo(n-1) + fibo(n-2)

def print_fibo(n): 
    print(fibo(n))

num_list = [31, 32, 33, 34]

pool = Pool(processes=4) 
pool.map(print_fibo, num_list) 

结果:

In[1]: runfile('D:/PYTHONcoding/test.py', wdir='D:/PYTHONcoding')

此结果似乎是一个无限循环。

我得到了“英特尔至强CPU / 16G RAM / 1080ti GPU /等”。 请让我知道如何使用Multiprocess.Pool。

3 个答案:

答案 0 :(得分:1)

您应在主模块中使用以下条件:

if __name__ == '__main__':
    pool = Pool(processes=4)
    pool.map(print_fibo, num_list)

进行此更改后,您的代码将输出(对我来说,在普通笔记本电脑上大约需要5秒):

1346269
2178309
3524578
5702887

答案 1 :(得分:0)

您的用法就可以了。我进行了进一步说明,然后在一个方便的集群上运行:

Calculated fibo( 31 ) =  1346269 with 4356617 calls
Calculated fibo( 32 ) =  2178309 with 7049155 calls
Calculated fibo( 33 ) =  3524578 with 11405773 calls
Calculated fibo( 34 ) =  5702887 with 18454929 calls

您正在拨打fibo的电话超过4000万次;响应速度可能会变慢,具体取决于正在运行哪个Xeon(R)。如果您想加快速度,请尝试动态编程/记忆:

次通话= 0 备忘录= {0:0,1:1}

def fibo(n):
    global calls, memo

    calls += 1
    # if n> 0 and n%10 == 0: print("ENTER n =", n)
    if n not in memo:
        memo[n] = fibo(n-1) + fibo(n-2)
    return memo[n]

输出:

Calculated fibo( 31 ) =  1346269 with 61 calls
Calculated fibo( 32 ) =  2178309 with 63 calls
Calculated fibo( 33 ) =  3524578 with 65 calls
Calculated fibo( 34 ) =  5702887 with 67 calls

答案 2 :(得分:0)

blhsing's answer确定了问题的根源:在Windows上,super().__init__需要为每个计算过程运行一个新的Python实例。每个新的Python都会加载定义各种功能的文件,然后等待产生它们的主控Python的指令,但是如果ObjA.__init__(test2)加载的Python文件无条件地产生了其他Python,而没有multiprocessing测试中,这些额外的Python产生了更多的Python,而它们又产生了更多的Python,没有结束。

(本质上,这里的问题是没有基本情况的递归。)

Prune's answer,建议记住,也是合理的。请注意,可以在没有全局变量的情况下进行记忆。有关预打包的版本,请参见What is memoization and how can I use it in Python?。我喜欢用作一个演示,它利用了您可以在函数上设置属性的事实:

multiprocessing

我们会预先处理基本案例,以避免递归。然后,将参数if __name__ == '__main__'(可能是数字)转换为def fibo(n): if n <= 1: return 0 if n < 1 else 1 ns = str(n) if not hasattr(fibo, ns): setattr(fibo, ns, fibo(n - 1) + fibo(n - 2)) return getattr(fibo, ns) n的字符串ns。如果无法获得提示的答案,则通过递归调用进行设置。然后我们返回记忆的答案。