c# - 始终使用await (`await x; await x; ....` ) vs .Result 在第一次await (`await x; x.Result; x.Result; ....` )之后?

标签 c# async-await

下面两个代码片段有什么区别吗?

1:使用await一直以来

await Task.WhenAll(x, y);
var a = await x;
var b = await y;
(await x).f();
(await y).g();

2:使用.Result第一个之后await .

await Task.WhenAll(x, y);
var a = x.Result;
var b = y.Result;
x.Result.f();
y.Result.g();

最佳答案

两者之间不会有任何行为差异,因为这两个任务都保证在 Task.WhenAll 之后完成。

编译器似乎没有意识到这一点,并在第一种情况下生成了一个稍微复杂的状态机(我通过查看生成的 IL 验证了这一点,请参阅 here for a proof )。

但是,这几乎不会产生任何明显的性能差异。

(从风格上来说,我更喜欢使用多个等待,因为在异步代码中看到 .Result 会敲响各种警钟)。

更新:正如 Stephen Cleary 在他的回答中解释的那样 here如果任务失败,await xx.Result 的行为会有所不同(不同的异常类型)。但这并不适用于此,因为任何失败的任务都已经使 await Task.WhenAll(...) 抛出异常。

关于c# - 始终使用await (`await x; await x; ....` ) vs .Result 在第一次await (`await x; x.Result; x.Result; ....` )之后?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/74325567/

相关文章:

c# - 创建通用存储库的异步版本

c# - Parallel.ForEach 是否使用 ASP.NET 线程池中的线程?

C# 动态映射输入文件的方法

c# - 使用 EPPlus 合并单元格?

c# - 在 .net c# 中异步或并行地在数据库中保存记录

c# - 是否有一种通用方法来定义既不接收 Action 也不接收 Func<Task> 的方法?

c# - IAsyncEnumerable 中缺少 await 运算符时的警告消息

c# - 字符串插值是否评估重复使用?

c# - 为什么 Entity Framework 尝试将 Guid id 转换为十进制?

c# - 如何为远程 Service Fabric 集群创建 actor 代理