首页 >后端开发 >Python教程 >Python多处理和并行编程指南

Python多处理和并行编程指南

Lisa Kudrow
Lisa Kudrow原创
2025-02-19 08:26:11447浏览

Python多处理和并行编程指南

加速计算是每个人都想实现的目标。如果您的脚本可以比目前的运行时间快十倍,该怎么办?在本文中,我们将研究Python多处理和一个名为多处理的库。我们将讨论什么是多处理,其优势以及如何通过使用并行编程来改善Python程序的运行时间。

好吧,让我们走吧!

>

钥匙要点

并行计算是一种通过同时使用CPU的多个内核来加速计算的方法。这可以通过多处理在Python中实现,该模块允许创建多个进程,每个过程都在单独的核心上运行。
    。 Python的多处理模块提供了诸如高度密集型任务的CPU使用更好的好处,与线程相比,对儿童流程的更多控制以及适合并行编程的任务的实施方便。 Python多处理并不总是比串行计算更有效。对于低CPU密集型任务,由于流程之间的计算引入的开销,串行计算的速度可以更快。 Python中的多处理模块为每个任务创建一个新的过程,需要同时执行。每个过程都有自己的Python解释器和内存空间,可以独立于其他过程运行。
  • 在Python中进行多处理可以大大提高程序的速度和效率,但它也会提高代码的复杂性。并非所有任务都适合并行化,在某些情况下,创建和管理多个流程的开销大于潜在的性能增长。
  • 平行概论
  • >在我们深入研究Python代码之前,我们必须谈论并行计算,这是计算机科学中的一个重要概念。
  • >通常,当您运行Python脚本时,您的代码在某个时候变成一个过程,并且该过程在CPU的单个核心上运行。但是现代计算机有多个核心,那么,如果您可以使用更多的核心进行计算怎么办?事实证明,您的计算会更快。
  • >
  • >现在将其作为一般原则,但是后来,在本文中,我们将看到这不是普遍的真实。
  • >
>没有介绍太多细节,并行性背后的想法是以一种可以使用CPU多个内核的方式编写代码。

使事情变得更容易,让我们来看一个示例。

>

>平行和串行计算

想象您有一个巨大的问题要解决,您一个人。您需要计算八个不同数字的平方根。你做什么工作?好吧,您没有很多选择。您从第一个数字开始,然后计算结果。然后,您继续与其他人一起。

>如果您有三个擅长帮助您的数学擅长的朋友怎么办?他们每个人都会计算两个数字的平方根,并且您的工作将更容易,因为工作负载平均分布在您的朋友之间。这意味着您的问题将被更快地解决。

>

好吧,这一切都很清楚吗?在这些示例中,每个朋友代表CPU的核心。在第一个示例中,整个任务由您顺序解决。这称为串行计算。在第二个示例中,由于您总共使用四个内核,因此您正在使用并行计算。并行计算涉及处理器中多个内核之间的并行过程或过程的使用。

>

Python多处理和并行编程指南

并行编程的

模型

我们已经建立了什么是平行编程,但是我们如何使用它?好吧,我们在该并行计算之前说过,涉及处理器多个内核之间的多个任务,这意味着这些任务是同时执行的。在接近并行化之前,您应该考虑一些问题。例如,还有其他优化可以加快我们的计算吗?

>目前,让我们理所当然地认为并行化是您的最佳解决方案。并行计算中主要有三个模型:

    完全平行。这些任务可以独立运行,并且不需要彼此交流。
  • >
  • >共享记忆并行性。流程(或线程)需要进行交流,因此它们共享一个全球地址空间。>
  • 消息传递。流程需要在需要时共享消息。
  • 在本文中,我们将说明第一个模型,这也是最简单的。
> Python多处理:Python中的基于过程的并行性 在Python中实现并行性的一种方法是使用多处理模块。多处理模块使您可以创建多个过程,每个过程都使用其自己的Python解释器。因此,python多处理实现了基于过程的并行性。

>

>您可能听说过其他库,例如螺纹,这些库也与Python一起内置,但是它们之间存在着重要的差异。多处理模块会创建新的过程,而线程创建新线程。

在下一部分中,我们将研究使用多处理的优势。

>

使用多处理

的好处

以下是多处理的一些好处:

    在处理高CPU密集型任务时,CPU更好地使用了CPU 与线程相比,对儿童的控制更多
  • 易于编码
  • 第一个优势与性能有关。由于多处理创建了新的过程,因此您可以通过将任务划分为其他内核来更好地利用CPU的计算能力。如今,大多数处理器是多核处理器,如果您优化代码,可以通过并行解决计算来节省时间。
  • 第二个优势着眼于多线程的多处理替代方案。线程不是过程,这会带来后果。如果您创建线程,那么杀死它或甚至像正常过程一样中断它是危险的。由于本文的多处理和多线程之间的比较不在本文的范围内,因此我鼓励您对其进行一些进一步的阅读。
>

多处理的第三个优点是,鉴于您要处理的任务非常适合并行编程。

开始使用Python多处理

我们终于准备好编写一些Python代码!

>

我们将从一个非常基本的示例开始,我们将使用它来说明Python多处理的核心方面。在此示例中,我们将有两个进程:

>

父程进程。只有一个父程流程可以有多个孩子。

儿童过程。这是由父母产生的。每个孩子也可以有新孩子。

    >我们将使用子进程执行某个功能。通过这种方式,父母可以继续执行。
  • >
  • 一个简单的python多处理示例
  • 这是我们将用于此示例的代码:

在此片段中,我们定义了一个称为Bubble_Sort(数组)的函数。此功能是气泡排序算法的真正幼稚实现。如果您不知道它是什么,请不要担心,因为这并不重要。要知道的至关重要的是,这是一个有效的函数。

>

过程类

>从多处理中,我们导入类过程。该类代表将在单独的过程中运行的活动。确实,您可以看到我们已经通过了一些论点:

<span>from multiprocessing import Process
</span>
<span>def bubble_sort(array):
</span>    check <span>= True
</span>    <span>while check == True:
</span>      check <span>= False
</span>      <span>for i in range(0, len(array)-1):
</span>        <span>if array[i] > array[i+1]:
</span>          check <span>= True
</span>          temp <span>= array[i]
</span>          array<span>[i] = array[i+1]
</span>          array<span>[i+1] = temp
</span>    <span>print("Array sorted: ", array)
</span>
<span>if __name__ == '__main__':
</span>    p <span>= Process(target=bubble_sort, args=([1,9,4,5,2,6,8,4],))
</span>    p<span>.start()
</span>    p<span>.join()
</span>

> target = bubble_sort,这意味着我们的新过程将运行Bubble_sort函数

args =([[1,9,4,52,6,8,4],),这是作为参数传递给目标函数

的数组

>我们为流程类创建了一个实例,我们只需要启动该过程即可。这是通过编写p.start()来完成的。在这一点上,该过程已开始。
  • >在退出之前,我们需要等待子过程完成其计算。 JOIN()方法等待该过程终止。
  • >

    在此示例中,我们仅创建了一个子进程。您可能猜到,我们可以通过在过程类中创建更多实例来创建更多的子过程。

    池类

    如果我们需要创建多个流程来处理更多CPU密集型任务,该怎么办?我们是否总是需要明确等待终止?这里的解决方案是使用池类类。

    >池类允许您创建一个工作过程池,在下面的示例中,我们将研究如何使用它。这是我们的新示例:

<span>from multiprocessing import Process
</span>
<span>def bubble_sort(array):
</span>    check <span>= True
</span>    <span>while check == True:
</span>      check <span>= False
</span>      <span>for i in range(0, len(array)-1):
</span>        <span>if array[i] > array[i+1]:
</span>          check <span>= True
</span>          temp <span>= array[i]
</span>          array<span>[i] = array[i+1]
</span>          array<span>[i+1] = temp
</span>    <span>print("Array sorted: ", array)
</span>
<span>if __name__ == '__main__':
</span>    p <span>= Process(target=bubble_sort, args=([1,9,4,5,2,6,8,4],))
</span>    p<span>.start()
</span>    p<span>.join()
</span>
>在此代码段中,我们有一个立方体(x)函数,该函数仅采用整数并返回其平方根。容易,对吗?

然后,我们创建一个池类的实例,而无需指定任何属性。池类类别默认每个CPU核心创建一个进程。接下来,我们使用一些参数运行地图方法。

地图方法将立方体函数应用于我们提供的峰值的每个元素 - 在这种情况下,这是从10到N的每个数字的列表。

的巨大优势是,列表上的计算是并行完成的!

>

>充分利用Python多处理

创建多个过程和进行并行计算不一定比串行计算更有效。对于低CPU密集型任务,串行计算比并行计算快。因此,重要的是要了解何时应该使用多处理 - 这取决于您执行的任务。

为了说服您,让我们看一个简单的例子:>

此片段基于上一个示例。我们正在解决相同的问题,该问题正在计算n个数字的平方根,但有两种方式。第一个涉及Python多处理的使用,而第二个则没有使用。我们正在使用时间库中的perf_counter()方法来衡量时间性能。

在我的笔记本电脑上,我得到了这个结果:

如您所见,有一个以上的差异。因此,在这种情况下,多处理更好。
<span>from multiprocessing import Pool
</span><span>import time
</span><span>import math
</span>
N <span>= 5000000
</span>
<span>def cube(x):
</span>    <span>return math.sqrt(x)
</span>
<span>if __name__ == "__main__":
</span>    <span>with Pool() as pool:
</span>      result <span>= pool.map(cube, range(10,N))
</span>    <span>print("Program finished!")
</span>

>让我们在代码中更改某些内容,例如N的值。让我们将其降低到n = 10000,看看会发生什么。

>

这就是我现在得到的:

<span>from multiprocessing import Pool
</span><span>import time
</span><span>import math
</span>
N <span>= 5000000
</span>
<span>def cube(x):
</span>    <span>return math.sqrt(x)
</span>
<span>if __name__ == "__main__":
</span>    <span># first way, using multiprocessing
</span>    start_time <span>= time.perf_counter()
</span>    <span>with Pool() as pool:
</span>      result <span>= pool.map(cube, range(10,N))
</span>    finish_time <span>= time.perf_counter()
</span>    <span>print("Program finished in {} seconds - using multiprocessing".format(finish_time-start_time))
</span>    <span>print("---")
</span>    <span># second way, serial computation
</span>    start_time <span>= time.perf_counter()
</span>    result <span>= []
</span>    <span>for x in range(10,N):
</span>      result<span>.append(cube(x))
</span>    finish_time <span>= time.perf_counter()
</span>    <span>print("Program finished in {} seconds".format(finish_time-start_time))
</span>

发生了什么事?现在,多处理现在是一个不好的选择。为什么?

与解决的任务相比,通过在过程之间分配计算来引入的高架太多。您可以看到时间表现有多大的区别。

>

结论

在本文中,我们通过使用Python多处理来讨论了Python代码的性能优化。

首先,我们简要介绍了哪些并行计算是使用它的主要模型。然后,我们开始谈论多处理及其优势。最后,我们看到平行化计算并不总是最佳选择,并且应将多处理模块用于并行化CPU结合任务。与往常一样,考虑到您要面临的具体问题并评估不同解决方案的利弊是一个问题。

我希望您发现学习有关Python的多处理与我一样有用。

关于Python多处理和并行编程

的常见问题

>在Python中使用多处理的主要优点是什么?在处理CPU密集型任务时,这是特别有益的,因为它使该程序能够利用CPU的多个内核,从而显着提高了程序的速度和效率。与螺纹不同,多处理不会遭受Python中全局解释器锁(GIL)的困扰,这意味着每个过程都可以独立运行而不会受到其他过程的影响。这使得多处理在Python中进行并行编程的功能。

>

>如何使用Python中的多处理模块工作?同时执行。每个过程都有自己的Python解释器和内存空间,这意味着它可以独立于其他过程运行。多处理模块提供了许多类和功能,使创建和管理这些过程变得容易。例如,该过程类用于创建一个新的过程,而池类类用于管理一个工作过程。 > Python中多处理和多线程之间的主要区别在于它们如何处理任务。在多处理为每个任务创建一个新过程时,多线程在同一过程中创建一个新线程。这意味着,虽然多处理可以充分利用多个CPU内核,但多线程受到Python中的全局解释器锁(GIL)的限制,该python中只允许一次执行一个线程。但是,多线程仍然对I/O结合任务很有用,该程序花费大部分时间等待输入/输出操作完成。

>如何使用多处理模块的共享内存机制来实现Python中的过程之间的数据?这些包括值和数组类,这些类别允许分别创建共享变量和数组。但是,重要的是要注意,由于每个过程都有自己的内存空间,因此对共享变量进行的更改或一个过程中的数组的更改将不会反映在其他过程中,除非它们使用锁或其他由多处理模块提供的同步基原始人明确同步。在python中使用多处理的潜在陷阱是什么? Python可以大大提高您计划的速度和效率,它也带来了自己的挑战。主要陷阱之一是代码的复杂性增加。管理多个过程比管理单线程程序更复杂,尤其是在处理共享数据和同步过程时。此外,创建一个新过程比创建新线程更含有资源密集型,这可能会导致内存使用增加。最后,并非所有任务都适合并行化,在某些情况下,创建和管理多个流程的开销大于潜在的性能增长。

>我如何处理Python多处理的例外? python中多处理中的异常可能有些棘手,因为在子进程中发生的例外不会自动传播到父过程。但是,多处理模块提供了几种处理异常的方法。一种方法是使用过程类的is_alive()方法检查进程是否仍在运行。如果该方法返回false,则意味着该过程已终止,这可能是由于例外。另一种方法是使用该过程类的出口码属性,它可以提供有关为什么终止过程的更多信息。

我可以与其他python库多处理?其他Python库。但是,重要的是要注意,并非所有库都设计用于在多处理环境中。某些库可能不是线程安全的,也可能不支持并发执行。因此,检查您使用的库文档总是一个好主意,以查看它是否支持多处理。

>

>我如何在Python中调试多处理程序?

>调试Python中的多处理程序可能会具有挑战性,因为传统调试工具可能在多处理环境中无法正常工作。但是,您可以使用几种技术来调试程序。一种方法是使用打印语句或记录来跟踪程序的执行。另一种方法是使用PDB模块的set_trace()函数在代码中设置断点。您还可以使用支持多处理的专业调试工具,例如多处理模块的log_to_stderr()函数,它允许您将进程的活动记录到标准错误。操作系统?

是的,您可以在不同操作系统上使用Python中使用多处理。多处理模块是标准Python库的一部分,这意味着它可以在支持Python的所有平台上可用。但是,由于它们处理过程的差异,多处理模块的行为可能在不同的操作系统之间略有不同。因此,最好在目标操作系统上测试您的程序以确保其按预期运行。在Python中使用多处理包括:

- 避免在可能的情况下在过程之间共享数据,因为这可能会导致复杂的同步问题。

- 使用池类管理您的工作人员流程,因为它提供了一个更高级别的界面,该界面简化了创建和管理流程的过程。

- 始终通过调用流程类的join()方法来清理过程,该方法可确保该过程在程序继续之前完成。

- 正确处理异常,以防止您的程序出乎意料的崩溃。

- 彻底测试您的程序以确保其在多处理环境中正确工作。

>

以上是Python多处理和并行编程指南的详细内容。更多信息请关注PHP中文网其他相关文章!

声明:
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn