<blockquote>
<p>Why does multi-processing slow down a nested for loop in python?</p>
</blockquote>
<p><strong>创建进程是一项非常昂贵的系统操作</strong>。操作系统必须重新映射大量页面(程序、共享库、数据等),以便新创建的进程可以访问初始进程的页面。多处理包还使用进程间通信,以便在进程之间共享工作。这也很慢。更不用说所需的最终联接操作了。为了提高效率(即尽可能减少开销),使用多处理包的Python程序应该共享少量数据并执行昂贵的计算。
在您的情况下,您不需要多处理软件包,因为您只使用Numpy数组(请参阅下文)</p>
<blockquote>
<p>This is a slightly different approach where I use the numexpr library to do a faster linal.norm operation. For a single operation this approach reduces runtime by a factor of 10.</p>
</blockquote>
<p>Numexpr使用<em>线程</em>,而进程和线程比进程轻(即更便宜)。Numexpr还使用<em>积极优化</em>尽可能加快计算表达式的速度(CPython没有做到这一点)</p>
<blockquote>
<p>I don't understand why simply putting this operation in a nested for loop would decrease performance so dramatically?</p>
</blockquote>
<p>Python的默认实现是CPython,它是一个解释器。口译员通常非常慢(尤其是CPython)。CPython几乎不执行代码优化。如果您想要快速循环,那么您需要将它们编译为本机代码或JIT的替代方法。您可以使用<strong>Cython</strong>或<strong>Numba</strong>进行此操作。这两种方法可以提供简单的并行化程序的方法。在您的案例中,使用Numba可能是最简单的解决方案。您可以从查找<a href="http://numba.pydata.org/numba-doc/dev/user/examples.html" rel="nofollow noreferrer">example programs</a>开始</p>
<hr/>
<p>更新:如果Numpy的实现是多线程can,那么多处理代码可能会慢得多。实际上,每个进程将在一台有N个内核的机器上创建N个线程。因此,将运行N*N个线程。这种情况称为<strong>过度订阅</strong>,已知效率低下(由于抢占式多任务处理,尤其是上下文切换)。检查这一假设的一种方法是简单地查看创建了多少线程(例如,在Posix系统上使用hwloc工具),或者简单地监视处理器的使用情况</p>