使用 Async 和 Await 的异步编程(C# 和 Visual Basic)
使用异步编程时,可以在可能需要长时间运行的代码指定点处理挂起,当程序的其他部分无法继续时。 此技术来避免可能的性能瓶颈并增强应用程序的总体响应能力。 Asynchrony到可能会阻塞事件很重要,例如,当程序访问该web。 如果该事件在块同步过程,整个程序块。 在异步,则当阻塞任务完成其工作时,进程,程序可以取得进展在其他方面。
因为所有与用户界面相关的事件通常共享一个线程,Asynchrony尤其重要的进程访问UI线程。 如果任何处理块,所有块。
Walkthrough: Accessing the Web by Using Async and Await (C# and Visual Basic) through the "To test the synchronous solution" section." data-guid="e3f8f9db89e40c395a4360cad8a04b26">对于块的示例中通过“测试同步解决方案”节处理,按照 演练:使用 Async 和 Await 访问 Web(C# 和 Visual Basic) 的步骤。 Async Sample: Accessing the Web Walkthrough and run the project that’s named SyncWalkthrough." data-guid="f26ad744ecfc12b69c3c928fcf571179">或者,您可以下载演练中的代码从 Async示例:访问Web演练 并运行名为SyncWalkthrough的项目。 当用户界面线程同步下载从web中的内容,无法移动控件或调整窗口的大小。 如果您不希望等待,不能即使关闭它关闭程序。
Async (Visual Basic) or async (C#) modifier and the Await (Visual Basic) or await (C#) operator are fundamental to async programming." data-guid="141ded8255c782aead709716ec234206">Async (Visual Basic)或 async (C#)修饰符和 等待 (Visual Basic)或 等待 (C#)运算符对异步编程是基本的。 async修饰符指示编译器方法或lambda表达式是异步的,并且可以使用请等待运算符指定在方法中悬挂点。 这种方法引用异步方法。在异步方法中,您可以等待运算符应用于特定任务挂起异步方法的执行,直到等待的任务完成。 同时,控件返回到异步方法的调用方。 finally blocks don’t run." data-guid="d3bb6d8d9350daab95d4781844dbf21d">保存并不构成从异步方法的退出,并且,编译器实现用于开发人员执行,包括注册挂起的方法中完成的延续的困难工作。 因此,异步代码容易编写,并且,如果您的程序保留类似于同步代码的逻辑结构。 例如,某些实例处理,例如循环,而异常处理,可能很难进行在传统异步代码编写。 在异步方法,解决您编写这些元素,因为在一个同步解决方案会并将问题。 TPL and Traditional .NET Asynchronous Programming." data-guid="da21bf25f8e9d0e9abed378633e7272f">有关asynchrony以前的方法的更多信息在.NET Framework,请参见 TPL 和传统 .NET 异步编程。
.NET Framework 4.5 包含与异步以及等待的许多成员。 Task or Task<TResult>." data-guid="373b1beed7013995f287dca26b0300f8">您可以通过附加到成员名称和 Task 或 Task<TResult>的返回类型“Async”后缀识别这些成员。 CopyToAsync, ReadAsync, and WriteAsync alongside the synchronous methods CopyTo, Read, and Write." data-guid="9efba51df2a62d561a0f33b02756f5c4">例如,System.IO.Stream选件类包含方法例如 CopyToAsync、ReadAsync和 WriteAsync 在同步方法 CopyTo、Read和 Write。
下面的示例通过比较同步编写与方法相同的方法声明此方法很简单,如果已编写以异步方式。 Walkthrough: Accessing the Web by Using Async and Await (C# and Visual Basic)." data-guid="67cae762c5d23b0c32a6c9e43e88700c">有关完整的示例,请参见演练:使用 Async 和 Await 访问 Web(C# 和 Visual Basic)。GetURLContents) to an asynchronous method (GetURLContentsAsync)." data-guid="752db01d008407e0cbe1dc764a12f91e">下面的更改将同步方法(以下方式更改方法签名。
Async or async modifier." data-guid="c236d110b31783159f85b76dac109d41">标记与 Byte() to Task(Of Byte()) in Visual Basic or from byte[] to Task<byte[]> in C#." data-guid="fe0144cf0bebda777d72a641a3d21f97">更改返回类型从 在异步操作完成时,任务是承诺提供的字节数组。 Async Return Types (C# and Visual Basic)." data-guid="3c68c063e78f40535bc82d55f399cf7b">有关异步的更多信息返回类型,请参见 异步返回类型(C# 和 Visual Basic)。
按照约定,添加后缀“Async”到方法的名称。
在方法体,请进行以下更改。
替换调用长时间运行的同步方法通过调用相应的异步方法。 GetResponse with a call to GetResponseAsync." data-guid="22c56cd356b155a33c960b22db7ecf67">在此示例中,将替换调用 GetResponse 在调用 GetResponseAsync。
Await or await operator to the result of the method call." data-guid="1bb171bea75227c426497bb1aeaf8a13">应用 CopyTo with a call to CopyToAsync." data-guid="41924fe0ee933984cce3157c63ba6330">替换调用 CopyTo 在调用 CopyToAsync。
Await or await operator to the result of the method call." data-guid="1bb171bea75227c426497bb1aeaf8a13">应用 转换完成。 Walkthrough: Accessing the Web by Using Async and Await (C# and Visual Basic)." data-guid="0cf7515bdd4a15819d3df6558981314f">有关完整的示例和分步说明,请参见 演练:使用 Async 和 Await 访问 Web(C# 和 Visual Basic)。
C# VB // Synchronous version of a method that downloads the resource that a URL // links to and then returns its content. private byte[] GetURLContents(string url){ // The downloaded resource ends up in the variable named content.var content = new MemoryStream(); // Initialize an HttpWebRequest for the current URL.var webReq = (HttpWebRequest)WebRequest.Create(url); // Send the request to the Internet resource, and wait for// the response.using (var response = webReq.GetResponse()) { // Get the data stream that is associated with the specified URL.using (Stream responseStream = response.GetResponseStream()) { // Read the bytes in responseStream, and copy them to content. responseStream.CopyTo(content); } } // Return the result as a byte array.return content.ToArray();}// Asynchronous version of the same method. The changed lines //are marked with **.// **Add the async modifier. Change the method name and the return type.privateasync Task<byte[]> GetURLContentsAsync(string url){ // The downloaded resource ends up in the variable named content.var content = new MemoryStream(); // Initialize an HttpWebRequest for the current URL.var webReq = (HttpWebRequest)WebRequest.Create(url); // **Call GetResponseAsync instead of GetResponse, and await the result.// GetResponseAsync returns a Task<WebResponse>.using (WebResponse response = await webReq.GetResponseAsync()) { // Get the data stream that is associated with the specified URL.using (Stream responseStream = response.GetResponseStream()) { // ** Call CopyToAsync instead of CopyTo, and await the response.// CopyToAsync returns a Task, not a Task<T>.await responseStream.CopyToAsync(content); } } // Return the result as a byte array.return content.ToArray();}Async or async modifier." data-guid="b787b3d3a1cd14a276b9a787901000c5">Await or await operator, but the absence of await expressions doesn’t cause a compiler error." data-guid="c1bdf44b07b6072121d3e8c078b97c3c">方法通常包含 如果异步方法不会将等待运算符指示悬挂点,则尽管"修饰符执行,一个同步方法。 编译器会发出此类方法的警告。 Async, async, Await, and await are contextual keywords." data-guid="0416c9af68ee0eb505c96c82a3c4e4b2">有关更多信息和示例,请参见以下主题:
Async (Visual Basic)
async(C# 参考)
Await 运算符 (Visual Basic)
await(C# 参考)
Sub procedure or a Function procedure that has a return type of Task or Task<TResult>. " data-guid="1c063944678a0407d2d19d6fb6d4e687">在Visual Basic中,异步方法是 sub 程序或具有 Task 或 Task<TResult>的一个返回类型的 功能 程序。void, Task, or Task<TResult>." data-guid="2f18b379ee6f5416527a0bd78a1385bd">在C#,异步方法可以具有 无效、Task或 Task<TResult>的返回类型。
Task or Task<TResult>." data-guid="779251d269accef20c506289f03d9e6a">若要使异步方法的调用方等待计算完成,请使用 Task 或 Task<TResult>的一个返回类型。 Task<TResult> as the return type if the method contains a Return (Visual Basic) or return (C#) statement that specifies an operand of type TResult." data-guid="c9527a94359e4e2ca1488406ec814619">您指定 Task<TResult>,因为返回类型,则方法包含指定类型 Task if the method has no return statement or has a return statement that doesn't return an operand." data-guid="47bd8ea3b86d6e672b2bdf4237edeea7">使用 Sub method (Visual Basic) or a void return type (C#) is used primarily to define event handlers, where a void return type is required." data-guid="215ed2901d69cc29cfd67a15f1e86725">Sub procedure or that has a void return type can’t be awaited, and the caller of a void-returning method can't catch any exceptions that the method throws." data-guid="35856b1928094deeeb505141fa82e6c3">是 ByRef parameters in Visual Basic or ref or out parameters in C#, but the method can call methods that have such parameters." data-guid="7db39fdd6b6c073a72d50be3cdcb433f">异步方法不能声明在 Visual Basic 或 ByRef parameters in Visual Basic or ref or out 参数或参数在 C#,但是,方法可以调用具有这些参数的方法。
Async Return Types (C# and Visual Basic)." data-guid="132ad1ba1e5fa891c07e1c69eae58f08">有关更多信息和示例,请参见异步返回类型(C# 和 Visual Basic)。 try-catch (C# Reference) or Try...Catch...Finally Statement (Visual Basic)." data-guid="8fb6e8fedcfacf63a5ec81399944a6a2">有关如何捕获异步方法的异常的更多信息,请参见 try-catch(C# 参考) 或 Try...Catch...Finally 语句 (Visual Basic)。
Async or async modifier. " data-guid="425c720e93d6c55dd04d5befe4297d15">按照约定,添加后缀“Async”在一个 您可以忽略事件、基类或接口协定建议一个不同的名称约定。 button1_Click." data-guid="8cf153d0525aa7c819337b89bebb96cb">例如,您不应向常用事件处理程序重命名,例如 异步方法旨在成为非阻塞操作。 当等待的任务运行时,在异步方法的一个等待表达式不会阻止当前线程。 相反,该表达式注册该方法的其余部分作为继续并返回控制对异步方法的调用方。因为异步方法本身并不会运行的线程,异步方法不需要多线程。 只有在方法处于活动状态,则方法在当前同步上下文中运行并使用在线程的时间。 Task.Run." data-guid="4e923852031b833ea1d58a8081f8232a">有关如何移动异步方法或lambda表达式的信息移到后台线程,请参见 Task.Run。
Task.Run." data-guid="4e923852031b833ea1d58a8081f8232a">
Task.Run." data-guid="4e923852031b833ea1d58a8081f8232a">
Task.Run." data-guid="4e923852031b833ea1d58a8081f8232a">(注:文章整理自MSDN)