スレッドプールには固定数のスレッドがあります。これらのスレッドは、共有リストから頻繁にwriteおよびreadにする必要があります。
この場合、Java.util.concurrent
パッケージのどのデータ構造(リストであることが望ましい、モニターなしである必要があります)は、この場合に最適ですか?
List
の方がよい
onlyJava.util.concurrent
のList
実装は CopyOnWriteArrayList です。 Travis Webbが言及しているように、同期リストのオプションもあります。
そうは言っても、List
である必要がありますか?コンカレントQueue
sとMap
sにはさらに多くのオプションがあり(Set
sからMap
sを作成できます)、これらの構造は多くの共有データ構造でやりたいことの種類。
キューの場合、膨大な数のオプションがあり、どのオプションを使用するかによって最適なオプションが異なります。
Javaコレクションは、次のようにスレッドセーフにすることができます。
List newList = Collections.synchronizedList(oldList);
または、新しいスレッドセーフリストを作成するには:
List newList = Collections.synchronizedList(new ArrayList());
リストのサイズが固定されている場合は、 AtomicReferenceArray を使用できます。これにより、スロットに対してインデックス付き更新を実行できます。必要に応じて、リストビューを作成できます。
ConcurrentDoublyLinkedList をご覧になるとよいでしょう。PaulMartinの「実用的なロックフリーの二重リンクリスト」に基づいてDoug Leaが作成しました。 Java.util.Listインターフェースを実装していませんが、Listで使用するほとんどのメソッドを提供します。
Javadocによると:
Deque(ダブルエンドキュー)の同時リンクリスト実装。同時挿入、削除、およびアクセス操作は、複数のスレッド間で安全に実行されます。イテレータは 弱い一貫性、イテレータの作成時以降のある時点での両端キューの状態を反映する要素を返します。彼らはConcurrentModificationExceptionを投げるnotを行い、他の操作と同時に進行するかもしれません。
ConcurrentLinkedQueue
は、ロックフリーキューを使用します(新しい CAS命令 に基づいています)。
設定が十分な場合、 ConcurrentSkipListSet が使用される場合があります。 (その実装は ConcurrentSkipListMap に基づいており、これは スキップリスト を実装しています。)
予想される平均時間コストは、包含、追加、および削除操作のlog(n)です。サイズ方法は、一定時間の操作ではありません。