蟒蛇。多处理池。如何获得所有结果

时间:2018-08-30 20:32:55

标签: python

开始使用Python并遇到一种愚蠢的情况。 我的函数返回两个值。我希望使用MP来加快执行速度。

import time
import multiprocessing as mp

def foo(bar, baz):
    print("start")
    time.sleep(2)
    print("end")
    return bar, baz


if __name__ == '__main__':
    pool = mp.Pool(processes=4)

    ret = []
    i = 0
    while i < 4 :
        j = i + 1
        while j < 4 :
            results = [pool.apply_async(foo, args=(i, j))]
            j = j + 1
        i = i + 1

    output = [p.get() for p in results]
    print(output)

最后,我想同时获得一个返回值的列表,例如[(0,1),(0,2),...]。但是我只看到一对。知道如何立即更改此代码以得到所有结果并且不丢失并行性吗? 谢谢!

start
start
start
start
end
start
end
start
end
end
end
end
[(2, 3)]

2 个答案:

答案 0 :(得分:1)

您在每次迭代中都将覆盖results列表,但是您应该将其追加。这应该可以解决问题:

results = []
while i < 4 :
    j = i + 1
    while j < 4 :
        results.append(pool.apply_async(foo, args=(i, j)))
        j = j + 1
    i = i + 1

output = [p.get() for p in results]

答案 1 :(得分:1)

诊断

这是经过一些调试的代码,并使用for语句以提高可读性:

for i in range(4):
    for j in range(i+1, 4):
        results = [pool.apply_async(foo, args=(i, j))]
        print("TRACE", results]

output = [p.get() for p in results]
print("FINAL", output)

查看输出,您可以看到问题:尽管您制作了6个不同的结果收集器,但是result只是在任何给定时间的最新收集器。您需要全部选拔。

输出:

TRACE [<multiprocessing.pool.ApplyResult object at 0x7faf4b711390>]
TRACE [<multiprocessing.pool.ApplyResult object at 0x7faf4b7114e0>]
TRACE [<multiprocessing.pool.ApplyResult object at 0x7faf4b711588>]
TRACE [<multiprocessing.pool.ApplyResult object at 0x7faf4b711630>]
TRACE [<multiprocessing.pool.ApplyResult object at 0x7faf4b7116d8>]
start
TRACE [<multiprocessing.pool.ApplyResult object at 0x7faf4b711780>]
start
start
start
end
end
start
start
end
end
end
end
FINAL [(2, 3)]

解决方案

“仅”使用嵌套循环列表推导来获取所需的结果应用程序列表:

results = [pool.apply_async(foo, args=(i, j))
              for i in range(4)
                 for j in range(i+1, 4)
          ]
print("TRACE", results)

output = [p.get() for p in results]
print("FINAL", output)

输出:

TRACE [<multiprocessing.pool.ApplyResult object at 0x7f52af945390>, 
       <multiprocessing.pool.ApplyResult object at 0x7f52af945438>, 
       <multiprocessing.pool.ApplyResult object at 0x7f52af9454e0>, 
       <multiprocessing.pool.ApplyResult object at 0x7f52af945588>,  
       <multiprocessing.pool.ApplyResult object at 0x7f52af945630>, 
       <multiprocessing.pool.ApplyResult object at 0x7f52af9456d8>]
start
start
start
start
end
end
end
end
start
start
end
end
FINAL [(0, 1), (0, 2), (0, 3), (1, 2), (1, 3), (2, 3)]