map 上的 Python 多处理

标签 python python-3.x

我刚刚研究了这个文档部分enter link description here

据我了解这个功能

import multiprocessing
pool = multiprocessing.Pool()
print pool.map(f, range(10))

将创建一个任务 block ,其数量等于核心数量。结果将与从序列中获取输入的顺序相同。

文档还说---将阻塞直到完成:

让我们想象上面的 f 是一个复杂的函数。我们有 4 个 CPU,因此 block 大小为 4,它是否会阻塞,直到所有 4 个都完成,然后才获取下一个 block ?

那么在最坏的情况下,3 个空闲核心会空闲很长时间,直到最后一个核心完成为止?

最佳答案

您似乎认为 chunksize 将与核心数量匹配。这是不正确的。如果未指定,chunksize 具有一个实现定义的值,并且它不等于核心数量,至少在 CPython(引用解释器)上是这样。在撰写本文时,在 Python 2.7 和 3.7 上,使用的计算为:

    if chunksize is None:
        chunksize, extra = divmod(len(iterable), len(self._pool) * 4)
        if extra:
            chunksize += 1

len(self._pool) 是工作进程的数量,len(iterable) 是输入可迭代对象中的项目数量(即 list 如果没有定义长度,则进行验证)。

因此,对于您的情况,计算结果为:

        chunksize, extra = divmod(10, numcores * 4)
        if extra:
            chunksize += 1

对于四核机器(例如),将计算 chunksize, extra = 0, 10,然后 if 检查将更改 chunksize1。因此,每个工作人员都会获取一个输入值(0、1、2 和 3 几乎会立即被抓取),然后当每个工作人员完成时,它会再抓取一项。假设所有项目花费的时间大致相同,您将在完全占用的情况下进行两轮(使用 4/4 个核心),然后在半占用的情况下进行一轮(使用 2/4 的核心) 。最坏的情况是最后一个开始的任务需要最长的运行时间。如果这是提前知道的,您应该尝试组织您的输入以防止这种情况发生(首先放置最昂贵的项目,因此在不完全占用的情况下运行的最终任务很短并且快速完成,从而最大化并行性);否则,这是不可避免的。

对于大量任务,是的,默认的 block 大小将会增加,例如对于四个核心上的 100 个输入,您的 chunksize7,生成 15 个 block ,其中最后一个 block 尺寸过小。所以,是的,对于运行时间差异很大的任务,您将面临占用率低的长尾风险。如果存在风险,请将您的 chunksize 显式设置为 1;它会降低整体性能(使其更接近 imap 的性能),但它消除了一个工作线程在一个 block 中处理 7 项中的第 1 项而所有其他核心都处于空闲状态的可能性。

关于 map 上的 Python 多处理,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53271511/

相关文章:

python - 如何使用 S3 Select 和制表符分隔的 csv 文件

python - 每秒打印功能?

python - django.core.exceptions.SuspiciousFileOperation : The joined path is located outside of the base path component

python - 如何在 Windows 上安装 pip3?

python - Peewee 在迁移过程中不使用主键递增整数字段

python - 删除具有 3 个或更多列且为 0 的记录

python - 从 TensorFlow 中高效地获取梯度?

Python 异步 IO 图像处理

php - 树莓派相机流媒体不会从 php 开始

python - 从字符串中仅删除完全匹配的子字符串