2013-12-08 24 views
2

我想了解如何鎖定在Java ConcurrentHashMap中工作。根據源代碼here,它看起來像是每次讀取都使用該特定段的鎖定來鎖定讀取器。我弄錯了嗎?ConcurrentHashMap在每次讀取時鎖定?

V readValueUnderLock(HashEntry<K,V> e) { 
    lock(); 
     try { 
      return e.value; 
     } finally { 
      unlock(); 
     } 
    } 

回答

2

每次讀取時不低於鎖定的方法readValueUnderLock

的文檔讀取下鎖條目的值字段。 如果有值字段 看起來爲空。這隻有在編譯器碰巧對 重新排序HashEntry初始化時纔有可能,其表格分配是 法定存儲器模式下但不知道是否曾發生過

讀入ConcurrentHashMap不會在整個地圖上同步。除了在一個條件下,Infact遍歷不會同步。內部LinkedList實現知道對基礎集合的更改。如果它在遍歷期間檢測到任何這樣的更改,它將在它正在遍歷的存儲桶上同步它自己,然後嘗試重新讀取這些值。這總能確保收​​到的價值總是新鮮的,如果有的話,還有簡約鎖定。

下面是獲得這一類readValueUnderLock實現被稱爲只有當v是空

V get(Object key, int hash) { 
    if (count != 0) { // read-volatile 
     HashEntry<K,V> e = getFirst(hash); 
     while (e != null) { 
      if (e.hash == hash && key.equals(e.key)) { 
       V v = e.value; 
     if (v != null) 
      return v; 
     return readValueUnderLock(e); // recheck 
      } 
      e = e.next; 
     } 
    } 
    return null; 
}