为了账号安全,请及时绑定邮箱和手机立即绑定

C#中的异步/等待机制

C#中的异步/等待机制

C#
qq_遁去的一_1 2022-11-21 21:50:57
我有2个问题想问。我在 Microsoft 文档中读过这段关于 async/await 的内容。但是我没看清楚。https://learn.microsoft.com/en-us/dotnet/csharp/programming-guide/concepts/async/task-asynchronous-programming-model#BKMK_APIAsyncMethods“如果 GetStringAsync(以及 getStringTask)在 AccessTheWebAsync 等待它之前完成,则控制权保留在 AccessTheWebAsync 中。如果被调用的异步进程 (getStringTask) 已经完成并且 AccessTheWebSync 不必等待,则暂停然后返回到 AccessTheWebAsync 的费用将被浪费为了最终的结果。”你能解释一下吗?正如我所读,当您在 C# 中使用 async/await 时,代码不会在两个单独的线程中运行。它仍然在同步上下文中,但它会在遇到“await”关键字的情况下返回 Task 作为在完成之前返回结果的承诺。如果任务在“等待”之前完成,现在与同步相同。没有区别。即使从调用方方法切换到“AccessTheWebAsync”方法(反之亦然)的成本也很高。抱歉,这是我第一次在 StackOverflow 上提问。
查看完整描述

2 回答

?
慕容3067478

TA贡献1773条经验 获得超3个赞

鉴于功能:


async Task<int> AccessTheWebAsync()  

{   

    // You need to add a reference to System.Net.Http to declare client.  

    using (HttpClient client = new HttpClient())  

    {  

        Task<string> getStringTask = client.GetStringAsync("https://learn.microsoft.com");  


        DoIndependentWork();  


        string urlContents = await getStringTask;  


        return urlContents.Length;  

    }  

}   

当执行到


string urlContents = await getStringTask; 

执行可以做两件事之一:

  1. 如果 GetStringAsync() 已经完成,则继续执行下一行(return urlContents.Length;)

  2. 如果 GetStringAsync() 尚未完成,则 AccessTheWebAsync() 的执行将暂停并返回到调用函数,直到 GetStringAsync() 完成。您询问的段落说明如果我们无论如何都暂停了 AccessTheWebAsync() 的执行,那么暂停然后返回到 AccessTheWebAsync 的费用将被浪费。 因此这不会发生,因为它足够聪明,知道什么时候暂停执行,什么时候不暂停执行。


查看完整回答
反对 回复 2022-11-21
?
慕少森

TA贡献2019条经验 获得超9个赞

C# 中的异步方法必须始终返回一个任务,如下所示:


public async Task method();

public async Task<bool> asyncMethod();

当它不返回任何东西时,void 就返回Task,在任何其他情况下Task<returntype>


当你调用异步方法时,你可以做三件事:


// Result is now of type Task<object> and will run async with any code beyond this line.

// So using result in the code might result in it still being null or false.

var result = asyncMethod();


// Result is now type object, and any code below this line will wait for this to be executed.

// However the method that contains this code, must now also be async.

var result = await asyncMethod();


// Result is now type Task<object>, but result is bool, any code below this line will wait.

// The method with this code does not require to be async.

var result = asyncMethod().Result;

所以来回答你的问题。


考虑执行代码的结果是否在代码的其他地方使用,因为如果你不等待它,结果将被浪费,因为它仍然是 null。


反之亦然,当等待一个不会返回任何东西的方法时,通常不需要等待。


查看完整回答
反对 回复 2022-11-21
  • 2 回答
  • 0 关注
  • 66 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信