HashMap put方法原始碼解析

2021-10-04 23:22:49 字數 2755 閱讀 8382

先上原始碼

public v put(k key, v value)
這裡先呼叫了hash方法得到key的hash值(並不是直接得到key的hash,具體可以看hash方法)

然後呼叫了內部putval方法,hash,key,value引數不需要多說,onlyifabsent 引數 if true, don』t change existing value(翻譯過來就是 如果為true則不要更改現有值)

if (!onlyifabsent || oldvalue == null)

//這裡判斷了onlyifabsent

e.value = value;

evict 引數 if false, the table is in creation mode.(如果為假,則該錶處於建立模式。不知道是幹啥的)

putval方法原始碼

final v putval(int hash, k key, v value, boolean onlyifabsent,

boolean evict)

if (e.hash == hash &&

((k = e.key) == key || (key != null && key.equals(k))))

break;

p = e;}}

v oldvalue = e.value;

if (!onlyifabsent || oldvalue == null)

e.value = value;

afternodeaccess(e);

return oldvalue;}}

++modcount;

if (++size > threshold)

resize();

afternodeinsertion(evict);

return null;

}

判斷當前table是否為null,或者長度===0 如果是就呼叫resize()方法擴容

根據hash確定需要插入table的位置 (i = (n - 1) & hash) 如果該位置未空 就直接插入

if ((p = tab[i = (n - 1) & hash]) == null)
需要插入位置不為空,找出需要插入或修改的點賦值給nodee,最後再修改e

3-1. hash值相同且(插入元素key與該位置元素key相等或equals為true),說明該位置的元素需要被新元素替換(在table同乙個位置的元素hash值不一定相同)

if (p.hash == hash &&

((k = p.key) == key || (key != null && key.equals(k))))

e = p;

3-2. 如果插入位置元素型別為紅黑樹,則呼叫treenode的puttreeval方法
else if (p instanceof treenode)

e = ((treenode)p).puttreeval(this, tab, hash, key, value);

3-3. 不滿足3-1和3-2,那麼該位置就是鍊錶(可能只有乙個元素),對其進行迴圈

for (int bincount = 0; ; ++bincount) 

if (e.hash == hash &&

((k = e.key) == key || (key != null && key.equals(k))))

//如果在該鍊錶中找到需要替換的節點

break;

p = e;

}

如果找到需要替換的節點(即put的key已存在),修改該節點的value,然後返回舊的value

v oldvalue = e.value;

if (!onlyifabsent || oldvalue == null)

e.value = value;

afternodeaccess(e);

return oldvalue;

}如果沒有執行步驟4就是沒有找到需要替換的節點(即put的key在table中不存在),屬於新增新的節點情況

++modcount;   

if (++size > threshold)

//如果節點數量超過閾值就會擴容

resize();

afternodeinsertion(evict);

return null;

這是紅黑樹結點的put方法

首先要知道一點,hashmap中的紅黑樹還是雙向鍊錶結構

找到插入點

插入平衡調整

/**

* tree version of putval.

*/final treenodeputtreeval(hashmapmap, node tab,

int h, k k, v v)

//tiebreakorder方法是比較k與pk的hashcode來賦值給dir

dir = tiebreakorder(k, pk);

}// 沒有找到與入參相同的節點,就插入節點

treenodexp = p;

if ((p = (dir <= 0) ? p.left : p.right) == null)

}}

hashmap put 方法 原始碼分析

public v put k key,v value 如果key null 執行nullkey 操作 if key null return putfornullkey value 通過key 計算 hash值 int hash sun.misc.hashing.singlewordwangjenki...

原始碼解析 HashMap put方法解析

1.算出key的hash值,key的hashcode的高低位異或算出來。2.若果雜湊表為空,則初始化雜湊表。3.算出雜湊表下標位置,n 1 hash。4.雜湊表下標位置值為空,則把傳入的引數封裝成node節點設定到雜湊表下標位置。5.如果該雜湊表下標的值不為空,如果key和hash值與傳入的值相等,...

js方法原始碼

去除html標籤 function removehtmltag str ie8相容placeholder標籤 不能輸入以0開頭的正數且不能輸入0,否則返回空字串 input name helpclass.seq keyup function else ps 不能輸入以0開頭的正整數但是可以輸入0的正...