我对 async/await 编程还很陌生,有时我觉得我理解它,然后突然间发生了一些事情,让我陷入了困境。
我正在测试 winforms 应用程序中进行尝试,这是我拥有的一个片段版本。这样做会阻塞 UI
private async void button1_Click(object sender, EventArgs e)
{
int d = await DoStuffAsync(c);
Console.WriteLine(d);
}
private async Task<int> DoStuffAsync(CancellationTokenSource c)
{
int ret = 0;
// I wanted to simulator a long running process this way
// instead of doing Task.Delay
for (int i = 0; i < 500000000; i++)
{
ret += i;
if (i % 100000 == 0)
Console.WriteLine(i);
if (c.IsCancellationRequested)
{
return ret;
}
}
return ret;
}
现在,当我通过将“DoStuffAsync()”的主体包装在 Task.Run 中进行轻微更改时,它工作得很好
private async Task<int> DoStuffAsync(CancellationTokenSource c)
{
var t = await Task.Run<int>(() =>
{
int ret = 0;
for (int i = 0; i < 500000000; i++)
{
ret += i;
if (i % 100000 == 0)
Console.WriteLine(i);
if (c.IsCancellationRequested)
{
return ret;
}
}
return ret;
});
return t;
}
综上所述,处理这种情况的正确方法是什么?
最佳答案
当你写这样的代码时:
private async Task<int> DoStuffAsync()
{
return 0;
}
这样您就可以同步执行操作,因为您没有使用 await
表达式。
注意警告:
This async method lacks 'await' operators and will run synchronously. Consider using the 'await' operator to await non-blocking API calls, or 'await Task.Run(...)' to do CPU-bound work on a background thread.
根据警告建议,您可以这样修改:
private async Task<int> DoStuffAsync()
{
return await Task.Run<int>(() =>
{
return 0;
});
}
要了解有关 async/await 的更多信息,您可以查看:
- Async and Await通过斯蒂芬克利里
- Asynchronous Programming with Async and Await来自 msdn
关于c# - 使用 async/await 时防止 winforms UI 阻塞,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33587832/