我试图并行化从集合发出的工作,并等待所有任务的完成。
这基本上就是我所拥有的:
public Task<int> DoWorkAsync(int arg){
return Task.Factory.StartNew(()=> {
Thread.Sleep(1000);
return arg*2;
});
}
public async void DoAllWorks(){
ICollection<int> workToDo = GetSomeWorkFromSomewhere();
IEnumerable<Task<int>> tasks = workToDo.Select(i=> DoWorkAsync(i));
int[] results = await Task.WhenAll(tasks);
Debug.Write(results.Sum()); // Never called
}
public void Main(){
DoAllWorks();
// rest of code, which is called
OtherMethods();
}
但是,WhenAll
方法会立即退出,其余代码也会运行,即使仍有工作正在执行。
如何解决?
答案 0 :(得分:2)
您正在使用async void
,它只能用于事件处理程序。
使用async void
时,您无法等待async
操作完成(同步或异步)。这意味着它“触发”DoAllWorks
并继续前进,因为它无法知道DoAllWorks
何时完成。 <{1}}内的await Task.WhenAll(tasks)
等待正常,但调用方法已经开始了。
在这种情况下,您应该返回一个可以DoAllWorks
或await
的任务,因为Wait()
本身不能是Main
。
async
答案 1 :(得分:0)
除事件处理程序外,不应使用async void。如果您返回一个任务,您可以使用await
关键字在主方法中等待它,或者像:
DoAllWorks().Wait();
仅供参考,您无需使用Thread.Sleep(1000);
。您可以稍微重写一下代码,以便与async/await
construct
return Task.Run(async ()=> {
await Task.Delay(1000);
return arg*2;
});