hashmap :先說hashmap,hashmap是執行緒不安全
的,在併發環境下,可能會形成環狀鍊錶
hashtable : hashtable和hashmap的實現原理幾乎一樣,差別無非是1.hashtable不允許key和value為null;2.hashtable是執行緒安全的。
但是hashtable執行緒安全的策略實現代價卻太大了,簡單粗暴,get/put所有相關操作都是synchronized的,這相當於給整個雜湊表加了一把大鎖,多執行緒訪問時候,只要有乙個執行緒訪問或操作該物件,那其他執行緒只能阻塞,相當於將所有的操作序列化,在競爭激烈的併發場景中效能就會非常差。
hashtable效能差主要是由於所有操作需要競爭同一把鎖,而如果容器中有多把鎖,每一把鎖鎖一段資料,這樣在多執行緒訪問時不同段的資料時,就不會存在鎖競爭了,這樣便可以有效地提高併發效率。這就是concurrenthashmap所採用的"分段鎖
"思想。
concurrenthashmap採用了非常精妙的"分段鎖"策略,concurrenthashmap的主幹是個segment陣列。
segment類似於hashmap,乙個segment維護著乙個hashentry陣列
成員變數在看hashmap的原始碼的時候基本上已經講解過了
基本上所有的構造方法最終會呼叫當前方法
public concurrenthashmap(int initialcapacity,
float loadfactor, int concurrencylevel)
//segmentshift和segmentmask這兩個變數在定位segment時會用到
this.segmentshift = 32 - sshift;
this.segmentmask = ssize - 1;
//初始化大小是否大於最大值
if (initialcapacity > maximum_capacity)
initialcapacity = maximum_capacity;
int c = initialcapacity / ssize;
if (c * ssize < initialcapacity)
++c;
int cap = min_segment_table_capacity; //2
while (cap < c)
cap <<= 1;
//建立 segments cap*loadfactor 擴容閥值 cap hashentry大小
segments0 =
new segment(loadfactor, (int)(cap * loadfactor),
(hashentry)new hashentry[cap]);
//建立segments陣列
segment ss = (segment)new segment[ssize];
unsafe.putorderedobject(ss, sbase, s0);
this.segments = ss;}
put方法講解(unsafe自己可以去看一下)
public v put(k key, v value)
//找到對應的segment 如果沒有則建立乙個
private segmentensuresegment(int k) }}
return seg;
}final v put(k key, int hash, v value, boolean onlyifabsent)
break;
}e = e.next;
}else
}} finally
return oldvalue;}
get方法 (不需要加鎖)
public v get(object key)
}return null;}
總結看懂了put方法 其他的方法都很easy 自己看 本文不做講解
concurrenthashmap主要使用segment來實現減小鎖粒度,把hashmap分割成若干個segment,在put的時候需要鎖住segment,get時候不加鎖,使用volatile來保證可見性,當要統計全域性時(比如size),首先會嘗試多次計算modcount來確定,這幾次嘗試中,是否有其他執行緒進行了修改操作,如果沒有,則直接返回size。如果有,則需要依次鎖住所有的segment來計算。
ConcurrentHashMap原始碼詳解
成員變數private static final int maximum capacity 1 30 private static final int default capacity 16 static final int max array size integer.max value 8 pr...
concurrentHashMap原始碼分析
concurrenthashmap是hashmap的執行緒安全版本,內部也是使用 陣列 鍊錶 紅黑樹 的結構來儲存元素。相比於同樣執行緒安全的hashtable來說,效率等各方面都有極大地提高。在這裡可以使用上篇那個 進行測試,根據結果可以知道concurrenthashmap是執行緒安全的,由於分...
ConcurrentHashMap原始碼分析
concurrenthashmap原始碼分析concurrenthashmap是乙個執行緒安全的 高可用hashmp 本部落格基於jdk1.8concurrenthash實現原理進行分析,如有不對,敬請斧 正。1 資料結構知識點 1 hash演算法 2 鍊錶 3 陣列 4 二叉樹 紅黑二叉樹 2 多...