并行的for和异步方法
本文关键字:异步方法 for 并行 | 更新日期: 2023-09-27 18:10:35
我有以下一个简单的问题-为什么异步方法不等待并行循环完成?
public async Task<List<object>> DoSomeAsync()
{
// some async actions with streams and web requests
// ...
ConcurrentQueue<object> queue = new ConcurrentQueue<object>();
Parallel.For(1, x, async i =>
{
// a little chunk of code
// ...
queue.Enqueue(new object());
// ...
// a little chunk of code again
}
return queue.ToList(); // debugger says that this statement is executed earlier than parallel loop.
}
你知道如何等待并行循环的执行吗?
不使用'async':这将是确保在移动到下一行之前完成过程的最简单方法,仍然处于并行执行模式(换句话说,它阻塞了主UI,等待工作进程完成,工作进程本身正在并行模式下运行一些东西):
Parallel.For(1, x, (i) =>
{
// a little chunk of code
// ...
queue.Enqueue(new object());
// ...
// a little chunk of code again
});
此外,您可以看看Alexandra Rusina (http://blogs.msdn.com/b/csharpfaq/archive/2010/06/01/parallel-programming-in-net-framework-4-getting-started.aspx)使用Task.Factory.ContinueWhenAll()
应用于您的问题(在并行/异步模式下运行的情况下)给出的示例。祝好,
由于Parallel.For
理想地并行执行多个任务,因此等待单个任务是没有意义的,因为这将固有地序列化它们的执行。为什么ParallelLoopResult
不是Task的子类,虽然对我来说是个谜。而你可以这样写
await Task.Run(() => Parallel.For(...)
它不会给你买任何东西,因为你已经在一个异步方法中,无论你的线程还是由Task.Run
创建的线程是坐在那里阻塞Parallel.For
的线程,在这一点上是无关紧要的。
我能想到的最好的是ParallelLoopResult
是这样写的,它需要一个线程来收集循环的状态。