29

我已经阅读了很多关于 async 和 await 的内容,起初我没有明白,因为我没有正确理解线程或任务。但是在掌握了两者之后,我想知道:为什么要使用async/await如果您对线程感到满意,为什么还要使用?

async/await 的异步可以通过线程信号Thread.Join()等来完成。它仅仅是为了节省编码时间和“减少”麻烦吗?

4

5 回答 5

24

是的,它是一种语法糖,使处理线程变得更加容易,也使代码更易于维护,因为线程管理是由运行时完成的。await立即释放线程并允许该线程或另一个线程从它停止的地方继续,即使在主线程上完成。

像其他抽象一样,如果您想完全控制幕后的机制,那么您仍然可以使用线程信号等自由地实现类似的逻辑。

如果您有兴趣查看async/await生成的内容,则可以使用 Reflector 或 ILSpy 反编译生成的代码。

阅读async 和 await 生成什么?有关 C# 5.0 代表您所做的事情的描述。

于 2013-08-18T12:30:51.547 回答
16

如果 await 只是调用Task.Wait,我们就不需要特殊的语法和新的 API。主要区别是async/await在等待完成时完全释放当前线程。在异步 IO 期间,根本不涉及线程。IO 只是内核内部的一个小数据结构。

async/await在底层使用基于回调的等待,并使其所有的讨厌(想想 JavaScript 回调......)走上一条路。

请注意,异步不只是将工作移动到后台线程(通常)。它释放所有涉及的线程。

于 2013-08-18T14:06:02.170 回答
11

比较asyncawait螺纹就像比较苹果和管扳手。从 10,000 英尺看,它们可能看起来很相似,但它们是针对不同问题的截然不同的解决方案。

async并且await都是关于异步编程的;具体来说,允许方法在等待某些操作时暂停自身。当方法暂停时,它会返回给它的调用者(通常是返回一个任务,该任务在方法完成时完成)。

我假设您熟悉线程,这是关于管理线程的。世界上与线程最接近的并行asyncTask.Run,它开始在后台线程上执行一些代码并返回一个任务,该任务在该代码完成时完成。

async并且await经过精心设计,与线程无关。因此,它们在 WPF/Win8/WinForms/Silverlight/WP 应用程序的 UI 线程中工作得很好,保持 UI 线程响应而不占用线程池资源。它们在 ASP.NET 等多线程方案中也能很好地工作。

如果您正在寻找/的好介绍,我在我的博客上写了一篇asyncawait,其中包含指向其他推荐阅读的链接。

于 2013-08-19T05:10:42.077 回答
6

线程和异步/等待功能之间存在差异。

考虑一种情况,您正在调用网络以从网络获取一些数据。这里调用网络驱动程序的线程(可能在某些 svchost 进程中运行)保持自身阻塞,并消耗资源。

在 Async/await 的情况下,如果调用没有网络绑定,它会使用 SynchronizationContext 将整个调用包装到一个回调中,该回调能够从外部进程获取回调。这释放了线程,线程将可供其他事物使用。

异步和并发是两个不同的东西,前者只是在异步模式下调用某些东西,而后者实际上是 cpu 绑定的。当您需要并发性时,线程通常会更好。

我很久以前写过一篇博客来描述这些特性。 C# 5.0 vNext - 新的异步模式

于 2013-08-18T13:51:03.187 回答
4

async/await does not use threads; that's one of the big advantages. It keeps your application responsive without the added complexity and overhead inherent in threads.

The purpose is to make it easy to keep an application responsive when dealing with long-running, I/O intensive operations. For example, it's great if you have to download a bunch of data from a web site, or read files from disk. Spinning up a new thread (or threads) is overkill in those cases.

The general rule is to use threads via Task.Run when dealing with CPU-bound operations, and async/await when dealing with I/O bound operations.

Stephen Toub has a great blog post on async/await that I recommend you read.

于 2013-08-18T13:15:13.467 回答