C#

时间:2019-04-02 06:58:59

标签: c# asynchronous async-await

我想问两个问题。

  1. 我已阅读Microsoft文档中有关异步/等待的这一段。但是我并不清楚。

https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/concepts/async/task-asynchronous-programming-model#BKMK_APIAsyncMethods

  

“如果GetStringAsync(因此getStringTask)在AccessTheWebAsync等待之前完成,则控制权仍保留在AccessTheWebAsync中。如果被调用的异步过程(getStringTask)已经完成并且AccessTheWebSync没有完成,则挂起然后返回到AccessTheWebAsync的开销将被浪费。必须等待最终结果。”

你能解释一下吗?

  1. 如我所读,当您在C#中使用async / await时,代码未在两个单独的线程中运行。它仍然处于同步上下文中,但是在遇到“ await”关键字的情况下将返回Task,以保证结果将一直返回到完成为止。如果任务在“等待”之前完成,则与同步相同。没有区别从调用方方法切换到“ AccessTheWebAsync”方法甚至是昂贵的,反之亦然。

对不起,这是我第一次在StackOverflow上提问。

2 个答案:

答案 0 :(得分:0)

C#中的异步方法必须始终返回Task,并且看起来像这样:

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。

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

答案 1 :(得分:0)

给出功能:

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://docs.microsoft.com");  

        DoIndependentWork();  

        string urlContents = await getStringTask;  

        return urlContents.Length;  
    }  
}   

执行到

string urlContents = await getStringTask; 

执行可以执行以下两项操作之一:

  1. 如果GetStringAsync()已经完成,则执行从下一行继续(返回urlContents.Length;)
  2. 如果GetStringAsync()尚未完成,则AccessTheWebAsync()的执行将被挂起,并且执行将返回到调用函数,直到GetStringAsync()完成。您要询问的那段说明,如果无论如何我们都暂停了AccessTheWebAsync()的执行,则会浪费暂停然后返回到AccessTheWebAsync的开销。因此,这不会发生,因为它很聪明足以知道何时暂停执行以及何时不暂停执行。