2012-01-09 2 views
4

接続文字列の配列をループし、各ループでいくつかの情報を抽出してリストに追加します。今、私はそれがマルチスレッドにするために、パラレルライブラリを使用したいが、私は、リストへの書き込みライブラリ保証はスレッドセーフであるかどうか、私はロックを使用する必要があるかどうかわからない:並列ライブラリを使用してリストに追加するときのスレッドの安全性を保証する正しい方法

List<SomeType> list = new List<SomeType>(); 

settings.AsParallel().ForAll(setting => 
{ 
    list.AddRange(GetSomeArrayofSomeType(setting)); /// DO I NEED TO DO LOCKING HERE??? 
}) 
+0

最初にこの複雑さを避け、 'list'に追加する設定をあらかじめ選択するのはなぜですか? –

+0

私はリストに設定を追加せず、設定ごとにいくつかの配列を取り出し、その配列の内容をメインリストに追加します。検索は長いプロセスかもしれないので、私はマルチスレッドが必要です – Andrey

答えて

10

書き込みのへリストは実際にマルチスレッドの書き込みには安全ではありません。アクセスを同期するにはlockを使用するか、マルチスレッドアクセス用に設計されたConcurrentQueueのようなコレクションを使用する必要があります。

ロックの例(listを想定し、メソッドのローカルである)

List<SomeType> list = new List<SomeType>(); 
settings.AsParallel().ForAll(setting => { 
    lock (list) { 
    list.AddRange(GetSomeArrayofSomeType(setting)); 
    } 
}); 

いっそ代わりForEach

var list = settings 
    .AsParallel() 
    .SelectMany(setting => GetSomeArrayOfSomeType(setting)) 
    .ToList(); 
のC#で
+1

SelectManyのために+1 – dtb

+0

ありがとう! – Andrey

+1

また、各タスクを独自のリスト(各リストを参照するスレッドが1つしかないため安全)に書き込んだり、最後のステップですべてのタスクを結合することもできます。追加の最初の束のために必要なゼロ同期があるので、これは勝つことができます。 –

関連する問題