3

ConcurrentHashMapスレッドセーフを提供しますが、ドキュメントの状態は次のとおりです。

「ただし、すべての操作はスレッドセーフですが、取得操作にはロックは必要ありません」

したがって、これから、キーと値の取得または設定はスレッドセーフであることがわかりますが、特定のキーの実際のVALUEを変更することはそうではありません(値によって、実際にはそのオブジェクトの値または状態を意味します)。

私はこれがどのように機能するかについて混乱しています。現時点では、このように機能すると思います。

キーのConcurrentHashMap唯一の保証は、キーの設定/取得に関してスレッドセーフです。ただし、マップ内に配置したオブジェクトは、それ自体で並行性を確保する必要があります。

これは正しいです?

4

3 に答える 3

3

ただし、マップ内に配置したオブジェクトは、それ自体で並行性を確保する必要があります。

あなたの理解は正しいです。

ドキュメントから:

ただし、すべての操作がスレッドセーフであっても、取得操作にはロックが必要ではなく、すべてのアクセスを妨げる方法でテーブル全体をロックすることはサポートされていません。

上記が言っていることは、読み取りが行われている間、ハッシュマップを自動ロックするための組み込みのメカニズムがないということです。特に、これは、get()操作が他のスレッドによって実行される同時変更と重複する可能性があることを意味します。

このドキュメントでは、並行性のセマンティクスについて説明しています。

取得操作(を含むget)は通常ブロックされないため、更新操作(およびを含む)と重複する場合がありputますremove。取得は、開始時に保持されている最後に完了した更新操作の結果を反映します。putAllおよびなどの集計操作のclear場合、同時取得は一部のエントリのみの挿入または削除を反映する場合があります。同様に、イテレータ/列挙の作成時または作成以降のある時点でのハッシュテーブルの状態を反映する要素Iteratorsを返します。Enumerations

于 2012-05-28T19:45:25.783 に答える
2

あなたの言うことはデフォルトで当てはまります。これらは外部からのオブジェクトであるため、マップがキーまたは値のいずれかのスレッドセーフを強制する方法はありません。ただし、オブジェクトの取得について読んだことは、その事実とは何の関係もありません。値の取得中にマップがブロックされないため、別の更新が同時に発生する可能性があります (これらの操作は重複する可能性があります)。

于 2012-05-28T19:47:18.667 に答える
1

ConcurrentHashMapの基本的な考え方は、変更のみがロックを使用し、取得のみの操作は使用しないということです。これが可能なのは、データ構造全体とその操作がget()、マップの「一貫性のある」状態のみを表示してその作業を実行できるように定義されているためです。現在進行中の挿入操作があるget()場合は、結果が表示されるか表示されませんが、部分的な結果や一時的に無効なデータが表示されることはありません。

于 2012-05-28T20:00:58.277 に答える