[英]Is async method synchronous if await Task is never returned?
我有一個在WPF應用程序中的UI線程上調用的構造函數。 在它內部,它調用async方法,但是必須以同步方式完成。 所以我試圖打電話給wait,但是造成了僵局,我明白原因。 因此,我介紹了表明方法應以異步還是同步方式運行的參數。 像這樣:
// constructor that is called on UI thread
public MyClass()
{
Method1(false).Wait();
}
public async Task Method1(bool runAsync)
{
await Method2(runAsync);
}
public async Task Method2(bool runAsync)
{
if (runAsync)
{
await Task.Run(() => Thread.Sleep(1000));
}
else
{
Thread.Sleep(1000);
}
}
我不想使用ConfigureAwait,因為我希望一切都在UI線程上運行。 將Method1(false).Wait(); 會導致死鎖(使用安全嗎)? 我測試了很多,但沒有測試,但是我不確定。 最后,我真正的問題是:如果從未執行過“ await Task.Run(...”),那么我的方法是否完全同步呢?我找到了與此主題相關的幾篇文章,但沒有一篇直接回答我的問題。
我有一個在WPF應用程序中的UI線程上調用的構造函數。 在它內部,它調用async方法,但是必須以同步方式完成。
我要在那里阻止你。 最好的解決方案是不要在UI線程上運行同步/阻塞代碼。 這會降低您的用戶體驗。 相反,您應該重組代碼,以使您永遠不會處於這種情況。
當顯示UI時,UI框架會要求您的代碼顯示數據。 您的代碼應同步運行並立即返回 (不阻塞)。 但是您的代碼還需要執行一些異步工作才能顯示數據。 因此那里存在沖突。
解決方案是為UI設計一種中間狀態,例如“正在加載...”消息或微調框。 然后,當您的代碼啟動時,它可以同步/立即顯示“正在加載”狀態(並啟動異步操作),並且當異步數據到達時,代碼會將 UI 更新為“最終”狀態。
我將在關於異步MVVM數據的文章中更詳細地討論這種模式。
與其在構造時花費大量精力解決異步問題(您的阻塞解決方案不是很好),何不編寫一個異步工廠來噴出這些對象呢?
class MyClass
{
public MyClass()
{
}
public async Task Method2(bool runAsync)
{
//async immediately
await Task.Delay(1000); //no Thread.Sleep. Blocking code != good
}
}
然后
public MyClassFactory
{
public async Task<MyClass> GetAsync()
{
var c = new MyClass();
await c.Method2();
return c;
}
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.