C# 死锁 TaskCompletionSource
程序员文章站
2023-11-06 10:25:52
在异步转同步时,使用不当容易造成死锁(程序卡死) 看如下案例: 有一个异步方法 在执行如上异步方法时,尝试将其转换为同步方法 按照官方文档《使用任务简化异步编程》,TaskCompletionSource使用步骤: 但是,以上逻辑执行时,界面会卡死!卡死效果如下,卡死的时候点击界面其它按钮无任何反应 ......
在异步转同步时,使用不当容易造成死锁(程序卡死)
看如下案例:
有一个异步方法
1 private static async task testasync() 2 { 3 debug.writeline("异步任务start……"); 4 await task.delay(2000); 5 debug.writeline("异步任务end……"); 6 }
在执行如上异步方法时,尝试将其转换为同步方法
按照官方文档《》,taskcompletionsource使用步骤:
- 获取var sourcetask =taskcompletionsource.task,
- 等待此sourcetask结果-sourcetask.result
- 设置设置sourcetask.result的结果值
1 private void taskcompletesourcedead_onclick(object sender, routedeventargs e) 2 { 3 awaitbytaskcompletesource(testasync()); 4 debug.writeline($"4. taskcompletesource_onclick end"); 5 } 6 private void awaitbytaskcompletesource(task task) 7 { 8 var taskcompletionsource = new taskcompletionsource<object>(); 9 var taskfromsource = taskcompletionsource.task; 10 task.continuewith(action => 11 { 12 taskcompletionsource.setresult(true); 13 }); 14 var task1result = taskfromsource.result; 15 debug.writeline($"3. awaitbytaskcompletesource end:{task1result}"); 16 }
但是,以上逻辑执行时,界面会卡死!卡死效果如下,卡死的时候点击界面其它按钮无任何反应。
为何会死锁?
猜测可能与task.wait()类似的死锁,详细如下:
- ui线程调用子线程并等待子线程结果,
- 子线程执行过程中,切换到了ui线程(因为testasync是在ui线程运行的)
- 从而导致两个线程均处在阻塞状态(死锁)
关键字:死锁、taskcompletionsource
上一篇: pandas 小数位数 精度的处理方法
下一篇: 拍摄爱情动作片的二十条基本规律(不黄)