[英]Await/async doesn't work as expected
我開始使用異步/等待。 我已經使用基於 MVVM 模式的 WPF 編寫了簡單的應用程序,但它沒有按我預期的那樣工作。 該程序的工作原理是沒有異步函數:執行執行函數后,它只會在循環函數結束后凍結和解凍。
請告訴我我做錯了什么部分。 我很感激任何反饋。 :)
這是我的模型視圖類。 它繼承自 wpf 類,該類包含 OnPropertyChanged 等標准 wpf 函數的定義。
public class ModelView : wpf
{
string _state;
public string state { get { return _state; } set { _state = value; OnPropertyChanged("state"); } }
public DelegateCommand work { get; set; }
public ModelView()
{
state = "Program started";
work=new DelegateCommand(_work);
}
async void _work(object parameter)
{
state = "Working...";
int j=await loop();
state = "Done: " + j;
}
async Task<int> loop()
{
int i;
for(i=0;i<1000000000;i++);
return i;
}
}
您的代碼中沒有異步部分。 簡單地使用async
關鍵字並不能做到這一點。 如果您希望將同步代碼卸載到不同的線程,請改用Task.Run
:
async void _work(object parameter)
{
status = "Working...";
int j=await Task.Run(() => loop());
status = "Done: " + j;
}
int loop()
{
int i;
for(i=0;i<1000000000;i++);
return i;
}
如果您確實有異步操作,則可以改用它:
async void _work(object parameter)
{
status = "Working...";
await Task.Delay(1000);
status = "Done: " + j;
}
指南:如果您的“異步”方法內部沒有await
,則它不是異步的。
你沒有做任何異步的事情。 async
關鍵字並不意味着“創建另一個線程”; 它相當復雜,但基本上它允許代碼在另一個異步操作完成時使用延續。 好的例子包括異步數據庫訪問、文件訪問、網絡訪問等。它還可以包括通過線程和Task.Run
異步長時間運行的操作。 但是:你沒有那樣做。 沒有不完整的await
——代碼只是在主線程上運行。 它僅在有不完整的內容要繼續時才安排延續。
引用編譯器(談論loop
方法):
警告此異步方法缺少“等待”運算符,將同步運行。 考慮使用 'await' 運算符來等待非阻塞 API 調用,或使用 'await Task.Run(...)' 在后台線程上執行 CPU 密集型工作。
看起來問題出在您的loop
函數上。 即使您已將其聲明為async
但其中沒有await
語句,並且您應該收到編譯器警告,正如@Marc Gravell 指出的那樣。
該函數通過大量循環迭代占用 UI 線程,這將導致阻塞,然后返回最終值。
所以你的循環函數實際上是一個同步函數。 假設您這樣做是為了測試目的,模擬async
操作的一個好方法是使用Task.Delay
。
例如:
async Task<int> loop()
{
await Task.Delay(5000);
return 1;
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.