Iva*_*azz 1 c# task async-await
任何人都可以向我解释这两种异步方法之间的区别吗?
方法A.
public async Task<List<Thumbnail>> GetAllThumbnailsAsync()
{
return await Task.Factory.StartNew(() =>
{
var imageUris = GetAllDirectoriesWithImageAsync(CommandBaseUri).Result;
return imageUris.Select(GetThumbnail).OrderByDescending(t => t.ImageDateTime).ToList();
});
}
Run Code Online (Sandbox Code Playgroud)
方法B.
public async Task<List<Thumbnail>> GetAllThumbnailsAsync()
{
var imageUris = await GetAllDirectoriesWithImageAsync(CommandBaseUri);
return imageUris.Select(GetThumbnail).OrderByDescending(t => t.ImageDateTime).ToList();
}
Run Code Online (Sandbox Code Playgroud)
据我所知,这两个方法都应该返回调用者并且不会阻止UI线程,但在这种情况下,只有方法A按预期工作,而方法B阻止我的UI.
我相信必须有一些基本概念,我可能在使用async/await时误解了.
任何人都可以开导我吗?
方法A基本上是在一个单独的任务中执行所有操作,这可能最终会出现在一个新线程中.当您等待结果任务时,您不会阻止任何事情.
方法B首先调用GetAllDirectoriesWithImageAsync,然后等待结果.这意味着在异步操作处理时,您不会阻止UI线程 - 但默认情况下,当您等待任务时,这意味着继续将在UI线程中运行.因此,imageUris.Select(...).OrderByDescending(...).ToList()将在UI线程中运行,我怀疑这是造成在UI问题的一部分.
现在,你可以调用.ConfigureAwait(false)在第一线的末端GetAllThumbnailsAsync,以表明你没有需要执行的UI线程上的第二部分-但将不能保证你不会在UI线程上执行的第二部分.相反,在我看来,你真的想要一种获取缩略图的异步方式.然后你可以这样做:
public async Task<List<Thumbnail>> GetAllThumbnailsAsync()
{
var imageUris = await GetAllDirectoriesWithImageAsync(CommandBaseUri)
.ConfigureAwait(false);
var thumbnailTasks = imageUris.Select(GetThumbnailAsync).ToList();
var thumbnails = await Task.WhenAll(thumbnailTasks).ConfigureAwait(false);
// I'm assuming there will be sufficiently few thumbnails here
// that sorting them on the UI thread wouldn't be a problem, in
// the unlikely event that we're *really* still on the UI thread by
// this point...
return thumbnails.OrderByDescending(t => t.ImageDateTime).ToList();
}
Run Code Online (Sandbox Code Playgroud)
请注意,我假设所有异步方法都是合理编写的,例如,GetAllDirectoriesWithImageAsync在返回任务之前不会执行大量的同步工作.
| 归档时间: |
|
| 查看次数: |
1220 次 |
| 最近记录: |