4

ConcurrentHashMapの実装に関する優れた概要を説明する記事「Javaの理論と実践:より良いHashMapの構築」を読んでいました。

また、Stackoverflowでいくつかの議論をここで見つけました。

ConcurrentHashMapが使用されている「シナリオ/アプリケーション/場所は何ですか」ということを頭に入れていましたが、疑問に思います。

ありがとうございました

4

3 に答える 3

6

マップを使用して複数のスレッドを計画することを除いて、を使用ConcurrentHashMapするのと同じインスタンスでを使用します。HashMap

于 2010-11-02T17:13:27.353 に答える
2

たとえば、マルチスレッドサーバーでユーザーIDからユーザーオブジェクトをすばやく検索するために使用します。

ネットワークスレッド、定期的なタスク用のタイマースレッド、およびコンソール入力を処理するためのスレッドがあります。複数のスレッドがユーザーのハッシュマップにアクセスするため、スレッドセーフである必要があります。

于 2010-11-02T17:08:06.507 に答える
2

ConcurrentHashMap次の理由により、大規模なマップまたは多数の読み取り/書き込み操作に使用することをお勧めします。

  • マップから読み取るとき、それはロックされていません。したがって、5つのスレッドがそこから読み取っている場合、それらすべてがマップから同時に読み取ることができます。
  • 書き込み時には、関連するレコード(キー)のみがロックされます。したがって、5つのスレッドが異なるキーの値を書き込んでいる場合、それらの操作はすべて同時に発生する可能性があります。ただし、2つのスレッドが同じキーに書き込んでいる場合、それらの操作はスレッドセーフです。これは、オブジェクト(マップ)レベルではロックが行われないが、ハッシュマップバケットレベルでははるかに細かい粒度で行われるために発生します。

次の例を考えてみましょう。

public class ConcurrentHashMapExample {

    public static void main(String[] args) {

        //ConcurrentHashMap
        Map<String,String> myMap = new ConcurrentHashMap<String,String>();
        myMap.put("1", "1");
        myMap.put("2", "1");
        myMap.put("3", "1");
        myMap.put("4", "1");
        myMap.put("5", "1");
        myMap.put("6", "1");
        System.out.println("ConcurrentHashMap before iterator: "+myMap);
        Iterator<String> itr1 = myMap.keySet().iterator();

        while(itr1.hasNext()){
            String key = itr1.next();
            if(key.equals("3")) myMap.put(key+"new", "new3");
        }
        System.out.println("ConcurrentHashMap after iterator: "+myMap);

        //HashMap
        myMap = new HashMap<String,String>();
        myMap.put("1", "1");
        myMap.put("2", "1");
        myMap.put("3", "1");
        myMap.put("4", "1");
        myMap.put("5", "1");
        myMap.put("6", "1");
        System.out.println("HashMap before iterator: "+myMap);
        Iterator<String> itr2 = myMap.keySet().iterator();

        while(itr2.hasNext()){
            String key = itr2.next();
            if(key.equals("3")) myMap.put(key+"new", "new3");
        }
        System.out.println("HashMap after iterator: "+myMap);
    }
}

出力は次のようになります。

ConcurrentHashMap before iterator: {1=1, 5=1, 6=1, 3=1, 4=1, 2=1}
ConcurrentHashMap after iterator: {1=1, 3new=new3, 5=1, 6=1, 3=1, 4=1, 2=1}
HashMap before iterator: {3=1, 2=1, 1=1, 6=1, 5=1, 4=1}
Exception in thread "main" java.util.ConcurrentModificationException
    at java.util.HashMap$HashIterator.nextEntry(HashMap.java:793)
    at java.util.HashMap$KeyIterator.next(HashMap.java:828)
    at com.test.ConcurrentHashMapExample.main(ConcurrentHashMapExample.java:44)

ご覧のとおり、現在反復しているマップを変更しようとすると、 HashMapaがスローされます。ConcurrentModificationException(具体的には、ステートメントで例外がスローされますString key = itr1.next();:)

于 2018-03-22T15:45:00.810 に答える