HashMap的擴容機制, ConcurrentHashMap和Hashtable主要區別


源代碼查看,有三個常量,

 static final int DEFAULT_INITIAL_CAPACITY = 16;

 static final int MAXIMUM_CAPACITY = 1 << 30;

 static final float DEFAULT_LOAD_FACTOR = 0.75f;

三個常量中可以看出,默認的容器大小是16,最大長度是230次方,load factor默認是0.75,擴充的臨界值是16*0.75=12

當我們往HashMapput元素的時候,先根據keyhashCode重新計算hash值,根據hash值得到這個元素在數組中的位置(即下標),如果數組該位置上已經存放有其他元素了,那么在這個位置上的元素將以鏈表的形式存放,新加入的放在鏈頭,最先加入的放在鏈尾。如果數組該位置上沒有元素,就直接將該元素放到此數組中的該位置上。

 

那么hashmap什么時候進行擴容呢?當hashmap中的元素個數超過數組大小*loadFactor時,就會進行數組擴容,loadFactor的默認值為0.75,也就是說,默認情況下,數組大小為16,那么當hashmap中元素個數超過16*0.75=12的時候,就把數組的大小擴展為2*16=32,即擴大一倍,然后重新計算每個元素在數組中的位置,而這是一個非常消耗性能的操作,所以如果我們已經預知hashmap中元素的個數,那么預設元素的個數能夠有效的提高hashmap的性能。

 

   ConcurrentHashMap和Hashtable主要區別就是圍繞着鎖的粒度以及如何鎖。如圖

左邊便是Hashtable的實現方式---鎖整個hash表;而右邊則是ConcurrentHashMap的實現方式---鎖桶(或段)。ConcurrentHashMap將hash表分為16個桶(默認值),諸如get,put,remove等常用操作只鎖當前需要用到的桶。試想,原來只能一個線程進入,現在卻能同時16個寫線程進入(寫線程才需要鎖定,而讀線程幾乎不受限制,之后會提到),並發性的提升是顯而易見.

 

想要對ConcurrentHashMap如何實現鎖粒度控制和如何鎖,還需研讀ConcurrentHashMap源碼。

 

 

 

 

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM