并发,并行和异步方法之间有什么区别?


196

并发使两个任务在单独的线程上并行运行。但是,异步方法并行运行,但在同一1个线程上。如何实现的?另外,并行性如何?

这三个概念之间有什么区别?


8
术语“异步”可能意味着很多不同的东西。这些术语是相关的,但它们并未描述不相交的事物集。含义重叠且因情况而异。
Pointy

2
因此,第一次并发同时运行两个或多个进程。这样一来,并发就不会并行。并行进程需要两个或多个内核,而并行进程可以在时间上共享一个内核。
瑞克·奥谢

Answers:


145

并发和并行实际上与您正确推测的原理相同,两者都与同时执行的任务有关,尽管我会说并行任务应该是真正的多任务处理,“同时”执行,而并发可能意味着任务正在共享执行线程,而看上去仍在并行执行。

异步方法与前两个概念没有直接关系,异步用于表示并发或并行任务的印象,但实际上,异步方法调用通常用于需要完成当前应用程序工作的过程,而我们不这样做不想等待并阻止我们的应用程序等待响应。

例如,从数据库获取数据可能会花费一些时间,但是我们不想阻塞UI来等待数据。异步调用获取一个回调引用,并在远程系统发出请求后立即将执行返回给您的代码。当远程系统执行所需的任何处理时,您的UI可以继续对用户作出响应,一旦将数据返回给回调方法,该方法就可以适当地更新UI(或移交该更新)。

从用户角度来看,它看起来像多任务处理,但可能并非如此。


编辑

可能值得补充的是,在许多实现中,异步方法调用将导致线程被启动,但这不是必需的,它实际上取决于正在执行的操作以及如何将响应通知给系统。


39
我认为您在第一段中混合了并行性和并发性。并发是指管理多个执行线程,其中并行性更具体而言是指多个执行线程同时执行。并发是更广义的术语,可以包含并行性。
Mark H

7
虽然这两个词非常相似,并且可能会混淆(并且经常是),但它们的定义却有所不同:并发=同时存在,同时发生或同时发生。由相同或不同的设备并行执行一次或多次执行的表观或实际性能或与之有关。如您所见,并行并不一定意味着并发,而可能看起来只是并发的。到最后,这些词经常互换使用,并且在n dev是一个房间的情况下,您可能会得到n + 1个定义;)
Lazarus

3
@Mehrdad如果您要根据市场营销材料中词典词的使用来定义词典词,那么我认为您可能会发现自己处于劣势。
Lazarus 2012年

8
错误。在编程的上下文中,并发是将代码“组合”为可以同时运行的逻辑位的能力。并行(与并发结合使用)正在获取所述代码并在100核计算机上运行它。
2014年

3
@FrankRadocaj正确。并发意味着可以将程序拆分为可以以任何顺序运行并具有确定结果的单元(单元本质上是线程)。并行意味着这些单元/线程实际上是在多个处理器上同时运行的。

93

简而言之,

并发是指多个任务,它们以重叠的时间段(没有特定的顺序)开始,运行和完成。并行是指多个任务或唯一任务的多个部分实际上在同一时间(例如在多核处理器上)运行。

请记住,并发和并行性不是一回事。

并发与并行之间的差异

现在让我们列出并发和并行之间的显着差异。

并发是指两个任务可以在重叠的时间段内启动,运行和完成。并行是指任务实际上在同一时间运行,例如。在多核处理器上。

并发是独立执行进程的组成,而并行是同时执行(可能相关)计算。

并发就是一次处理很多事情。并行是关于一次做很多事情。

一个应用程序可以是并发的,但不能是并行的,这意味着它可以同时处理多个任务,但不会同时执行两个任务。

一个应用程序可以是并行的,但不能是并发的,这意味着它可以同时处理多核CPU中一个任务的多个子任务。

一个应用程序既不能是并行的,也不能是并发的,这意味着它一次顺序地处理所有任务。

一个应用程序可以是并行的,也可以是并发的,这意味着它可以同时在多核CPU中同时处理多个任务。

并发

当我们谈论至少两个或更多任务时,并发本质上是适用的。当一个应用程序实际上能够同时执行两个任务时,我们将其称为并发应用程序。尽管这里的任务看起来像同时运行,但是从本质上讲它们可能不一样。它们利用操作系统的CPU时间分片功能,其中每个任务运行其任务的一部分,然后进入等待状态。当第一个任务处于等待状态时,CPU被分配给第二个任务以完成它的一部分任务。

因此,操作系统根据任务的优先级分配CPU和其他计算资源,例如内存;依次处理所有任务,并给他们完成任务的机会。对于最终用户,似乎所有任务都是并行运行的。这称为并发。

平行性

并行不需要两个任务存在。通过使用CPU的多核基础结构,通过为每个任务或子任务分配一个内核,它实际上可以同时运行部分任务或多个任务。

并行性本质上要求具有多个处理单元的硬件。在单核CPU中,您可能会获得并发性,但不能获得并行性。

异步方法

这与并发性和并行性无关,异步用于表示并发或并行任务的印象,但是有效地通常将异步方法调用用于需要在当前应用程序之外工作的进程,而我们不想等待并阻止我们的应用程序等待响应。


2
很有帮助。谢谢
Neha

我仍然对异步与并发感到困惑。我已经看到了“异步运行任务”和“同时运行任务”这两个短语。异步运行任务和同时运行任务似乎是同一回事吗?
Moondra

1
@Moondra异步任务在单个线程上运行,与多线程无关。异步任务将任务发送到应用程序外部的外部进程,即数据库,文件读取器……这些是IO进程,然后在该进程上添加回调,以在IO进程完成时执行操作。我不确定的是某些编程语言中的某些“异步”功能会在您调用异步任务时创建一个单独的新线程,我听说C#是其中一个,但我不确定,因此
Tobi Owolawi

65

并发是指交错执行多个任务,而不是依次逐个执行每个任务。

并行是指这些任务实际上是并行执行的。

在此处输入图片说明


异步是一个单独的概念(即使在某些情况下是相关的)。它指的是一个事件可能与另一个事件发生在不同的时间(而不是同步)。下图说明了同步执行和异步执行之间的区别,其中参与者可以对应于不同的线程,进程甚至服务器。

在此处输入图片说明

在此处输入图片说明


7
简单有效的插图。
contactmatt

1
并发与异步一样吗?

2
这两个概念确实非常接近,但并不相同。在实践中,异步与动作之间的交互作用(例如A和B)更为相关,其中一个动作(B)由另一个动作(A)触发,第二个动作是否等待第一个动作完成。并发是动作的更笼统术语,这些动作也可以彼此无关,也可以按顺序执行还是交错执行。
Dimos

1
因此,异步主要是关于阻塞和非阻塞
Daniel

19

在几种情况下可能发生并发:

异步—这意味着您的程序执行非阻塞操作。例如,它可以通过HTTP发起对远程资源的请求,然后在等待接收响应的同时继续执行其他任务。这有点像您发送电子邮件,然后继续生活而无需等待响应。

并行性-这意味着您的程序通过将工作分解为任务来利用多核计算机的硬件来同时执行任务,每个任务都在单独的内核上执行。有点像在洗澡时唱歌:实际上,您实际上在同时做两件事。

多线程—这是一种软件实现,允许同时执行不同的线程。即使多线程程序在单核计算机上运行,​​它似乎也同时在执行多项操作。这有点像通过各种IM窗口与不同的人聊天;尽管实际上是来回切换,但最终结果是您同时进行多个对话。


这些都是很好的类比!谢谢。可以说并发可以用您的多线程定义来定义吗?因此,并发=多线程在单核上看起来像是同时发生的,但是它真的在快速地来回切换吗?
wongz

17

每个人都在将异步与并行性或并发性相关联方面遇到麻烦,因为异步不是并行或并发的反义词。它是“同步”的反义词。这只是表明某个东西(在这种情况下为线程)是否将与其他东西(在这种情况下为另一个线程)同步。


6

并发意味着可以同时但不必同时执行多个任务。当您必须执行多个任务但又只有一个资源时,我们便开始并发。在单核环境中,并发是通过上下文切换来实现的。

并行性就像同时执行多个任务一样,就像您可以一起唱歌和洗澡一样。现在,您正在并行执行任务。

术语异步与线程执行有关。在异步模型中,执行一个任务时,您可以切换到其他任务,而无需等待上一个任务完成。

异步编程可以帮助我们实现并发。在多线程环境中进行异步编程是一种实现并行性的方法。


5

“同步和异步是编程模型。并发和并行是执行任务的方式...”。来源:https//medium.com/better-programming/sync-vs-async-vs-concurrent-vs-parallel-5754cdb60f66

换句话说,sync和async描述了程序在执行函数调用时的执行方式(它将等待还是继续执行?),而并发和并行描述了函数(任务)的执行方式(并发=可能在以下位置执行)同一时间,并行=有效地同时执行)。


媒介不是来源,而是其他人谈论他对某个主题的误解的文章,它并没有使他/她具有权威。
,全能的骆驼Moha

3
这是引文,因此是来源。这里的大多数答案不是由任何领域的权威人士撰写的,并且作者给出的解释足够好。
Pedro Boechat

在stackoverflow上,您至少拥有一个投票系统,并且它是一个由专业人士组成的社区。任何人都可以在媒体上写任何东西。两者之间不是公平的比较。
全能骆驼Moha

2
任何人都可以在这里写任何东西,我不知道您为什么选择Medium。无论如何,我是一名专业程序员,我支持这种理解。而且我觉得它很优雅,因为它相对较短。
Pedro Boechat

问题不在于Medium是不好的来源,而是在于仅链接到外部页面的答案不是答案。如果您详细阐述了引用的部分或总结了文章的内容,而不仅仅是链接到它,则可以大大改善此答案。
David Schwartz

4

并发

并发意味着应用程序同时(同时)在一项以上的任务上取得进展。好吧,如果计算机只有一个CPU,则应用程序可能无法在同一时间同时完成一项以上的任务,而是在应用程序中一次要处理多个任务。在开始下一项任务之前,它并没有完全完成一项任务。

平行性

并行是指应用程序将其任务分解为较小的子任务,这些子任务可以并行处理,例如在多个CPU上同时进行。

并发与并行的细节

如您所见,并发与应用程序如何处理其执行的多个任务有关。应用程序可以一次(顺序)处理一个任务,也可以同时(并行)处理多个任务。

另一方面,并​​行性与应用程序如何处理每个单独的任务有关。应用程序可以从头到尾顺序处理任务,或者将任务拆分为可以并行完成的子任务。

如您所见,应用程序可以是并发的,但不能并行。这意味着它可以同时处理多个任务,但是这些任务不会分解为子任务。

应用程序也可以是并行的,但不能是并行的。这意味着该应用程序一次只能处理一个任务,并且该任务被分解为可以并行处理的子任务。

另外,一个应用程序既不能是并发的也不可以是并行的。这意味着它一次只能处理一个任务,并且该任务永远不会分解为子任务以并行执行。

最后,应用程序也可以是并发和并行的,因为它既可以同时处理多个任务,又可以将每个任务分解为多个子任务以并行执行。但是,在这种情况下,并发性和并行性的某些好处可能会丢失,因为计算机中的CPU已经足够合理地仅使用并发性或并行性。结合使用它可能只会导致很小的性能提升甚至性能下降。在盲目采用并发并行模型之前,请确保进行分析和衡量。

来自http://tutorials.jenkov.com/java-concurrency/concurrency-vs-parallelism.html


4

这里需要清除一些语义:

并发或并行是资源争用的问题,而异步是关于控制流的问题

不同程序(或它们的组成的操作)被称为异步,当没有确定性执行其的顺序的处理; 换句话说,很可能在给定的时间T可以对它们中的任何一个进行处理。根据定义,多个处理器(例如CPU或Persons)可以同时处理其中的几个;在单个处理器上,它们的处理是交错的(例如线程)。

当异步过程或操作共享资源时,它们称为“并发” 。并发是在任何给定时间T竞争的绝对可能性。否则,必须解决并发控制问题。

因此,异步过程或操作可以与其他过程并行或同时进行。


4

平行 :这是一个广义术语,表示两段代码“同时”执行该代码。它是“真正的”并行性还是通过某种巧妙的设计模式伪造都没有关系。关键是您可以同时启动“任务”,然后分别控制它们(使用互斥锁和所有适当的技巧)。但是通常您更喜欢仅将“并行”一词用于“真正的”并行性,例如:通过非合作多任务(无论是CPU / GPU内核)还是仅在软件级别通过让OS管理它来实现在非常低的水平)。人们不愿意为伪造并行性的复杂顺序代码说“并行”,例如在浏览器窗口的javascript中会发现这种情况。因此,人们在这个线程中说“异步与并行性无关”的原因。可以,但是不要混淆它们。

并发:没有并行性就不可能有并发性(无论是模拟的还是真实的,如上所述),但是该术语专门针对以下事实:两个系统将在某个时间点尝试同时访问同一资源。它着重强调了您将不得不处理的事实。

异步:每个人都是对的,说异步与并行无关,但是它为它铺平了道路(使事情变得平行或不平行的负担在您身上-请继续阅读)。

“异步”指的是并行化的表示形式,它使并行化中通常涉及的三个基本方面形式化:1)定义任务的初始化(例如,启动时间以及获得的参数),2)完成后必须执行的操作,以及3)代码之间应该继续做什么。

但是它仍然只是语法(通常以回调方法表示)。在后台,底层系统可能会简单地决定这些所谓的“任务”只是要堆积的代码片段,直到完成当前正在执行的代码为止。然后,它们一个接一个地解堆并顺序执行它们。或不。它还可能为每个任务创建一个线程并并行运行它们。谁在乎?该部分不包含在概念中;)


3

我将简短扼要地介绍这些概念。

并发与并行-任务执行方式。

以现实生活中的例子为例:这是一个挑战,要求您既要吃整个大蛋糕,又要唱整首歌。如果您是唱整首歌并完成蛋糕的最快人,那么您将获胜。因此,规则是您同时唱歌和吃饭。您如何做不属于规则。您可以吃整个蛋糕,然后唱整首歌,也可以吃半个蛋糕,然后唱半首歌,然后再做一次,等等。

并行是一种特定的并发类型,其中任务实际上是同时执行的。在计算机科学中,并行性只能在多核环境中实现。

同步与异步-编程模型。

同步时,您将代码编写为从上到下依次执行的步骤。在异步编程模型中,您将代码编写为任务,然后并行执行。同时执行意味着所有任务都可能同时执行。


3

在这里我用一些例子解释


平行性

GPU使用并行处理来处理相同的代码块(AKA内核上千种物理和逻辑线程)。理想情况下,该过程同时开始和结束所有线程。没有超线程的单个CPU内核无法执行并行处理。

注意:我之所以说是理想的,是因为当您在具有6M线程的硬件上运行大小为7M的内核时,它必须在所有6M线程上并行运行两次相同的代码,同时每次消耗6M线程。

  • 一个内核(一段代码)在多个处理器上执行
  • 同时
  • 单一的执行顺序(一个内核必须做同样的事情中的所有线程,所以“支链”或“如果” s的避免,因为它们将通过建立大量的NOP(不操作的急剧消耗的资源)同步所有线程)
  • 本质上增加移动速度显着
  • 极大地限制了您可以做什么
  • 高度依赖硬件

注意:并行性不仅限于GPU。


并发

一个Web服务收到许多小请求,在实时性和需要处理这些请求的不同,在任何时间,并独立于其他请求或任何内部工作。但是,您希望Web服务始终启动并运行,而不破坏数据状态或系统运行状况。

想象一个用户更新一条记录,而另一个用户同时删除同一条记录。

  • 许多任务被执行
  • 实时(或每当一个请求到达)
  • 具有不同的执行顺序(与并行处理中的内核不同,并发任务可以执行不同的操作,您很可能必须对它们进行排队或对其进行优先级排序)
  • 从根本上提高了平均响应时间,因为任务2不必等待任务1完成
  • 本质上是牺牲了计算时间,因为许多任务在同一时间运行,并且资源有限
  • 需要正确地管理共享资源,以免死锁或破坏数据。

注意:这些请求通常消耗一些必不可少的资源,例如内存,数据库连接或带宽。但是,您希望Web服务始终保持响应状态。异步是使其响应而不是并发的关键


异步

如果一个繁重的进程(例如I / O操作)在GUI线程上运行,则很容易阻塞GUI(或其他基本线程)。为了保证UI响应能力,可以异步执行繁重的过程。这是更好地运行类似的异步操作一次一个。例如,如果同时运行多个IO绑定操作,可能会明显减慢速度,因此最好将它们完成排队以启动

  • 一个任务一批任务在另一个线程上执行
  • 一度
  • 如果有一项任务,那么就没有序列了,所以您要么等待它完成,要么一劳永逸
  • 如果这是一批任务,那么您可以同时解雇所有任务,等待所有任务完成,或者运行每个任务完成以启动
  • 由于开销,从根本上降低了性能
  • 提供对另一个线程的响应(有效防止UI线程或其他必要线程的阻塞)

注意:并发执行的异步操作(即一次执行一次以上)是并发操作。


注意:并发性和异步性常常相互混淆。并发是指系统的不同部分协同工作而不会互相干扰(这些问题通常通过锁,信号灯或互斥锁解决)。异步是您实现响应能力(例如线程)的方式。

*注意:异步和多线程经常相互混淆。异步代码不一定涉及新线程。它可以是硬件操作,也可以是Stephan所说的纯操作,请阅读此内容

例如,在下面的WPF + C#代码中,await Task.Run(()=> HeavyMethod(txt))正在解决异步问题,同时 textBox.Dispatcher.Invoke正在解决并发问题:

private async void ButtonClick(object sender, RoutedEventArgs e)
{
    // run a method in another thread
    await Task.Run(()=> HeavyMethod(txt));

    // modify UI object in UI thread
    txt.Text = "done";
}

// This is a thread-safe method. You can run it in any thread
internal void HeavyMethod(TextBox textBox)
{
    while (stillWorking)
    {
        // use Dispatcher to safely invoke UI operations
        textBox.Dispatcher.Invoke(() =>
        {
            // UI operations outside of invoke will cause ThreadException
            textBox.Text += ".";
        });
    }
}

2

并发与并行:在一个时间点的并发只能完成一项任务。示例:单个cpu处理器并行性我们可以完成多个任务。示例:双核或多核处理器

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.