2016-09-05 75 views
1

可以说我跑RunSynchron()。在这种情况下,它运行Delay(),暂停10秒,然后继续执行程序。完成Delay()后,它将为if-语句返回值1。但为什么我必须退回Task<int>而不是int为什么要返回任务<int>而不是int? (异步&等待)

class Synchron 
{ 
    public async void RunSynchron() 
    { 
     var delay = this.Delay(); 
     Console.WriteLine("Now we wait..."); 
     Console.WriteLine("But we can continue with our work"); 

     if(await delay == 1) 
      Console.WriteLine("Now it's done"); 

    } 

    public async Task<int> Delay() 
    { 
     await Task.Delay(10000); 
     return 1; 
    } 
} 
+0

这是编译器将结果包装到适当位置的方式MT环境 - 保留结果,以便知道它将从另一个线程进入。在MT环境下工作可以节省大量时间,结果仍然是一个整数! –

+0

http://blog.stephencleary.com/2012/02/async-and-await.html –

回答

0

因为async关键字就在它返回任务的方法的语法糖。这是它的定义。

在引擎盖下,当编译器在同一个方法调用中遇到await时,它会添加完全异步调用并等待任务完成。因此,编译器需要Task<int>为您构建代码,最终编译的代码。

请注意,以下代码await被编码为从该方法返回的任务的任务继续。如果你试图自己写,那就有很多样板。这就是为什么async/await关键字如此有用。

0

因为该函数没有返回一个整数,而是一个Task在以后返回一个整数。如果函数返回一个整数,你可以像调用函数那样调用函数,但这比真正执行的代码更像一个语法特征。

0

这是async/await特征的设计的一个不幸的方面是async似乎是该方法的声明的一部分。

我说不幸的,因为它是一个实施细节有关方法 - 具体地,它的变化可以这样的方法中出现的代码的性质,使得await s的允许出现和将适当地处理。

它不会更改方法的签名(实际上,它在接口声明中是不允许的)。因此,如果你有一个返回“something”的方法,并且在稍后的时间点,“something”可以被转换为int,那么你并没有描述返回int的方法。在你的例子中,你将这个“东西”存储在你的变量delay中。这一点不是int - 只是稍后可以变成int的东西。

他们本可以选择通过让async隐含地改变方法签名来将结果包装在Task中“更具魔力” - 但这会使得实际返回类型对于随意检查更不明显。如果想要将方法从async转换为非async或反之亦然,则还需要更多的实际编辑(您还必须编辑返回类型)