python并行遍历_如何在python中并行化big for循环

It seems that python would generate the list of arguments first, and then feed the list to the function “f”, even using xrange. Is that correct?

是的,因为您使用的是列表推导,它明确要求它生成该列表.

(请注意,xrange在这里并不是真正相关的,因为一次只有两个范围,每个范围都是10K;与参数列表的100M相比,没什么.)

如果希望它根据需要动态生成值,而不是一次生成所有100M,则要使用生成器表达式而不是列表推导.几乎总是将括号变成括号的问题:

x=pool.map(f,((i,j) for i in range(10000) for j in range(10000)))

但是,从the source中可以看到,如果给map提供一个生成器,map最终只会列出一个列表,因此在这种情况下,它什么也解决不了. (文档没有明确说明这一点,但是很难看到如果没有长度,如何选择合适的块大小将可迭代对象切成小段……).

而且,即使事实并非如此,结果仍然会再次遇到相同的问题,因为pool.map返回一个列表.

要解决这两个问题,可以改用pool.imap.它懒惰地消耗可迭代,并返回结果的惰性迭代器.

需要注意的一件事是,如果您不通过imap,imap不会猜测最佳的块大小,而只是默认为1,因此您可能需要一些思考或反复试验来优化它.

另外,imap仍会在输入结果时将它们排入队列,因此它可以按照参数的顺序将它们反馈给您.在病理情况下,它可能最终导致结果排队(poolsize-1)/ poolsize,尽管实际上这很少见.如果要解决此问题,请使用imap_unordered.如果您需要了解顺序,只需将参数与参数和结果来回传递即可:

args = ((i, j) for i in range(10000) for j in range(10000))

def indexed_f(index, (i, j)):

return index, f(i, j)

results = pool.imap_unordered(indexed_f, enumerate(args))

但是,我注意到在您的原始代码中,您对f(i,j)的结果根本不做任何事情.在那种情况下,为什么还要费心收集所有结果呢?在这种情况下,您可以返回循环:

for i in range(10000):

for j in range(10000):

map.apply_async(f, (i,j))

但是,imap_unordered可能仍然值得使用,因为它提供了一种非常简便的方法来阻止所有任务完成,同时仍使池本身处于运行状态以供以后使用:

def consume(iterator):

deque(iterator, max_len=0)

x=pool.imap_unordered(f,((i,j) for i in range(10000) for j in range(10000)))

consume(x)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值