9

ハッシュテーブルは同期されているため、スレッドセーフであると読みました。このコードスニペットを検討してください

if(!hashtable.contains(key)){
hashtable.put(key,value);
}

ハッシュテーブルの操作は同期されていない可能性があります。たとえば、t1 が put を実行する前にThread t1、hastable にアクセスしてキーをチェックし、同時にキーをチェックする場合。Thread t2現在、2 つのスレッドが if ブロック内にあり、キー値の上書きが発生しています。

そのため同期ブロックが必要です。

synchronized {
if(!hashtable.contains(key)){
    hashtable.put(key,value);
    }
}

この理解は正しいでしょうか?または、hastables に対して実行される操作に対して hastables safe です。競合状態に関するこの投稿を読んでいるときに、この疑問が生じました

4

2 に答える 2

13

synchronizedブロックが必要であることは正しいです。Hashtable'sメソッドはですが、ブロック外で複数のsynchronizedメソッドを呼び出すと、競合が発生する可能性があります。synchronized組み込みの同期により、たとえば 2 つのスレッドputが同時に呼び出された場合の問題が回避されます。

あなたも調べたいかもしれませんConcurrentHashMap

于 2013-10-07T21:04:27.567 に答える
4

Hashtableメソッドは同期されますが、競合状態に対するメソッドレベルの保護のみを提供します。(そのため、複数のスレッドが同時にデータを変更しようとしている場合、 — とは異なり、 — は内部的に破損することはありません。) スレッドセーフであるのは、この意味でのみHashtableです。HashMapHashtable

どちらHashtableConcurrentHashMap高レベルの同期を提供しません。これは通常、複数ステップの操作を実行するときに必要ですsynchronizedとにかく外部ブロックが必要なのでHashMapHashtable.

 * Jeff Storey が指摘しているように、コードで行っていることを正確に実行ConcurrentHashMapするメソッドがあります。putIfAbsent他のマルチステップ操作のConcurrentHashMap場合、必要なことをアトミックに行うメソッドがある場合とない場合があります。

于 2013-10-07T21:08:04.433 に答える