前言
瞭解到JDK8對HashMap進行了優化,就一起了解一下JDK8的HashMap。
原理
1. 哈希表的原理
首先需要一張Hash表,Java通過數據實現:默認長度位16,並且。
第一步插入張三(哈希值11):
第二步插入李四(哈希值12):
第三步插入李磊(哈希值12):
從上圖我們基本可以看出Java HashMap的存儲原理。
2. JDK8在什麼情況會將鏈表轉化成紅黑樹?
上圖中如果12這個位置的數據存放太多了,超過8個,這個時候Java 就會將鏈表轉化成紅黑樹,(這個要注意如果數組長度低於64是不會轉紅黑樹的)。
紅黑想要了解的同學轉:https://www.cnblogs.com/jssj/p/13873485.html
3. Hash 不可能一直是16 這麼長,那什麼時候擴容呢,Java代碼中寫了當存入數據超過hash表長度的3/4 就會擴容擴容的邏輯爲翻倍。
即:16 --> 32 --> 64 -- 128 這樣。
hash表擴容所有已經存的值的hsah值都需要重新計數,再放入新的hash表中, 這個操作比較消耗性能,所以這裏存在一個優化點。
如果我們知道map需要被使用的長度是多少,可以在創建HashMap的時候知道長度:
Map hashMap = new HashMap(64);
總結
1. JDK8 Hash表有自動擴容的功能。 擴容會重新將節點放入新的hash表中。
2. 底層數據結構:JDK8爲 數組+鏈表+紅黑樹,之前爲數組+鏈表。
3. JDK8中鏈表在長度超過8並且數組大於64的時候,自動由鏈表轉成紅黑樹。
4. Hash表在元素大於3/4 長度的時候進行Hash表擴容(每次翻倍)。
5. HashMap是線程不安全的,如果需要線程安全可以使用ConcurrentHashMap。