简体   繁体   English

为什么此异步/等待代码不会死锁

[英]Why this async/await code doesn't deadlock

I am reading this article about deadlock, and I tried with my own code and it doesn't have deadlock issue. 我读文章有关的僵局,我试图用我自己的代码,它没有死锁问题。 Why is that? 这是为什么?

I am expecting: 我期望:

  1. GetJsonAsync finishes await and about to return jsonString GetJsonAsync等待完成并即将返回jsonString

  2. Main is executing jsonTask.Result and hold the context Main是执行jsonTask.Result并保留上下文

  3. GetJsonAsync wants to return jsonString until context is available GetJsonAsync想要返回jsonString直到上下文可用

  4. deadlock will happen 死锁会发生

      public static void Main(string[] args) { var jsonTask = GetJsonAsync(); int i = jsonTask.Result; Console.WriteLine(jsonTask.Result); } public static async Task<int> GetJsonAsync() { var jsonString = await ReturnIntAsync(); return jsonString; } public static async Task<int> ReturnIntAsync() { int i = 0; await Task.Run(() => i++); return i; } 

It doesn't deadlock because there's no synchronizing SynchronizationContext , so the async method resumes executing on a thread pool thread, not the main thread. 它不会死锁,因为没有同步SynchronizationContext ,因此async方法恢复在线程池线程而不是主线程上执行。

Relevant quotes from the article (emphasis added): 文章中的相关引号(添加了重点):

Here's the situation: remember from my intro post that after you await a Task, when the method continues it will continue in a context. 情况就是这样:在我的介绍性帖子中,请记住,当您等待任务后,方法继续执行时,它将在上下文中继续进行。

In the first case, this context is a UI context (which applies to any UI except Console applications ). 在第一种情况下,此上下文是UI上下文(适用于除Console应用程序之外的任何UI)。 In the second case, this context is an ASP.NET request context... 在第二种情况下,此上下文是ASP.NET请求上下文...

For the UI example, the “context” is the UI context; 对于UI示例,“上下文”是UI上下文。 for the ASP.NET example, the “context” is the ASP.NET request context. 对于ASP.NET示例,“上下文”是ASP.NET请求上下文。 This type of deadlock can be caused for either “context”. 这种死锁可能是由于“上下文”引起的。

If you really want to deadlock a Console application this way, you can use AsyncContext from my AsyncEx library to install a single-threaded context on the main thread of your Console app. 如果您确实想以这种方式使控制台应用程序死锁,则可以使用AsyncEx库中的 AsyncContext在控制台应用程序的主线程上安装单线程上下文。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM