コレクションを並行して処理したいのですが、実装に問題があるため、助けを求めています。
並列ループのラムダ内で、C# で async とマークされたメソッドを呼び出したい場合に問題が発生します。例えば:
var bag = new ConcurrentBag<object>();
Parallel.ForEach(myCollection, async item =>
{
// some pre stuff
var response = await GetData(item);
bag.Add(response);
// some post stuff
}
var count = bag.Count;
この問題はカウントが 0 の場合に発生します。これは、作成されたすべてのスレッドが事実上単なるバックグラウンド スレッドであり、Parallel.ForEach
呼び出しが完了を待たないためです。async キーワードを削除すると、メソッドは次のようになります。
var bag = new ConcurrentBag<object>();
Parallel.ForEach(myCollection, item =>
{
// some pre stuff
var responseTask = await GetData(item);
responseTask.Wait();
var response = responseTask.Result;
bag.Add(response);
// some post stuff
}
var count = bag.Count;
動作しますが、await の賢さが完全に無効になり、手動で例外処理を行う必要があります.. (簡潔にするために削除されました)。
Parallel.ForEach
ラムダ内で await キーワードを使用するループを実装するにはどうすればよいですか? 出来ますか?
Parallel.ForEach メソッドのプロトタイプはAction<T>
as パラメーターを取りますが、非同期ラムダを待機させたいと考えています。