HashMap分析

分析源碼:android-28

Map:接口

HashMap是個(gè)散列鏈表萎庭。

put方法實(shí)現(xiàn)

HashMap在put的時(shí)候,先根據(jù)key的hashCode重新計(jì)算hash值忌傻。

根據(jù)hash值判斷要存放在鏈表數(shù)組的位置

Node<K,V> p = tab[i = (n - 1) & hash]

如果要存放的位置為null屁置,則直接放置到該位置。

如果不為空朗若,需要判斷

  • 兩個(gè)Node的hash值和key值是否相等恼五,如果相等,則直接覆蓋

  • 如果不相等哭懈,則插入到該位置鏈表的表尾(不同版本的代碼可能不同灾馒,之前的版本是插入到鏈表的表頭)

  • 如果鏈表過長,超過8之后遣总,會(huì)轉(zhuǎn)換成紅黑樹(暫時(shí)先略過睬罗,以后在研究)

由此可以得到HashMap注定不是一個(gè)有序的結(jié)構(gòu)

對于相同hash值,采用鏈表的形式存放旭斥,一定程度上容达,解決了hash沖突問題

image.jpeg

get方法實(shí)現(xiàn)

get(Object key)方法,也是用相同的方法獲取hash值垂券,找到該hash值對應(yīng)的位置花盐,并做出相應(yīng)的判斷

  • 如果對應(yīng)位置的Node<K,V>為空,則直接返回null

  • 如果有值

    • 先取出first的node菇爪,并判斷key值是否等于我們傳入的key值卒暂,如果相等則返回

    • 如果第一個(gè)不是我們需要的,就會(huì)一直按順序往下查找娄帖,直到找到或者鏈表結(jié)束返回null

resize擴(kuò)容

我平時(shí)習(xí)慣這樣寫

 Map<String, Object> map = new HashMap<>();

所以先以這種形式來分析擴(kuò)容的情況

public HashMap() {
  this.loadFactor = DEFAULT_LOAD_FACTOR; // all other fields defaulted
}

不帶參數(shù)的構(gòu)造函數(shù)也祠,沒有定義threshold(閾值)此時(shí) threshold=0

當(dāng)put一個(gè)鍵值對的時(shí)候,就是觸發(fā)擴(kuò)容操作

if (++size > threshold)
    resize();

重點(diǎn)來了=佟U┖佟!削葱!

final Node<K,V>[] resize() {
    Node<K,V>[] oldTab = table;
    int oldCap = (oldTab == null) ? 0 : oldTab.length;
    int oldThr = threshold;
    int newCap, newThr = 0;
    if (oldCap > 0) {
      // MAXIMUM_CAPACITY 為 1 << 30 2的30次方
      if (oldCap >= MAXIMUM_CAPACITY) {
          threshold = Integer.MAX_VALUE;
          return oldTab;
      }

      // 以第一次put為例奖亚,容量<< 1 擴(kuò)大為原來的2倍 此時(shí)oldCap為1,  則newCap為2  DEFAULT_INITIAL_CAPACITY = 16
      // 條件不符合
      else if ((newCap = oldCap << 1) < MAXIMUM_CAPACITY &&
             oldCap >= DEFAULT_INITIAL_CAPACITY)
              //如果之前的容量超過16析砸,則閾值直接設(shè)置為原來的2倍
              newThr = oldThr << 1; // double threshold
      }
      else if (oldThr > 0) // initial capacity was placed in threshold
              newCap = oldThr;
    else {               // zero initial threshold signifies using defaults
        newCap = DEFAULT_INITIAL_CAPACITY;
        newThr = (int)(DEFAULT_LOAD_FACTOR * DEFAULT_INITIAL_CAPACITY);
     }
  // 以上條件不符合直接運(yùn)行到這
    if (newThr == 0) {
        // loadFactor 默認(rèn)為0.75 newCap=2
        float ft = (float)newCap * loadFactor;
        // 得到新的閾值 如果newCap < MAXIMUM_CAPACITY 為ture 則值為后面的結(jié)果昔字,如果為false則值為0
        newThr = (newCap < MAXIMUM_CAPACITY && ft < (float)  MAXIMUM_CAPACITY ?
              (int)ft : Integer.MAX_VALUE);
      }
      // 賦值 閾值更新為 =(int)裝載因子*新的容量大小
    threshold = newThr;
    @SuppressWarnings({"rawtypes","unchecked"})
    Node<K,V>[] newTab = (Node<K,V>[])new Node[newCap];
   table = newTab;
    if (oldTab != null) {
       // 將之前的轉(zhuǎn)移到新的
        。。作郭。
    }
    return newTab;
}
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末陨囊,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子夹攒,更是在濱河造成了極大的恐慌蜘醋,老刑警劉巖,帶你破解...
    沈念sama閱讀 206,378評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件咏尝,死亡現(xiàn)場離奇詭異压语,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)编检,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,356評論 2 382
  • 文/潘曉璐 我一進(jìn)店門胎食,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人允懂,你說我怎么就攤上這事斥季。” “怎么了累驮?”我有些...
    開封第一講書人閱讀 152,702評論 0 342
  • 文/不壞的土叔 我叫張陵酣倾,是天一觀的道長。 經(jīng)常有香客問我谤专,道長躁锡,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 55,259評論 1 279
  • 正文 為了忘掉前任置侍,我火速辦了婚禮映之,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘蜡坊。我一直安慰自己杠输,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 64,263評論 5 371
  • 文/花漫 我一把揭開白布秕衙。 她就那樣靜靜地躺著蠢甲,像睡著了一般。 火紅的嫁衣襯著肌膚如雪据忘。 梳的紋絲不亂的頭發(fā)上鹦牛,一...
    開封第一講書人閱讀 49,036評論 1 285
  • 那天,我揣著相機(jī)與錄音勇吊,去河邊找鬼曼追。 笑死,一個(gè)胖子當(dāng)著我的面吹牛汉规,可吹牛的內(nèi)容都是我干的礼殊。 我是一名探鬼主播,決...
    沈念sama閱讀 38,349評論 3 400
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼晶伦!你這毒婦竟也來了碟狞?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 36,979評論 0 259
  • 序言:老撾萬榮一對情侶失蹤旧噪,失蹤者是張志新(化名)和其女友劉穎附帽,沒想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 43,469評論 1 300
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡载荔,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 35,938評論 2 323
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了悦冀。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片贤徒。...
    茶點(diǎn)故事閱讀 38,059評論 1 333
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖窟绷,靈堂內(nèi)的尸體忽然破棺而出锯玛,到底是詐尸還是另有隱情,我是刑警寧澤兼蜈,帶...
    沈念sama閱讀 33,703評論 4 323
  • 正文 年R本政府宣布攘残,位于F島的核電站,受9級特大地震影響为狸,放射性物質(zhì)發(fā)生泄漏歼郭。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,257評論 3 307
  • 文/蒙蒙 一辐棒、第九天 我趴在偏房一處隱蔽的房頂上張望病曾。 院中可真熱鬧,春花似錦漾根、人聲如沸泰涂。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,262評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽逼蒙。三九已至,卻和暖如春寄疏,著一層夾襖步出監(jiān)牢的瞬間其做,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 31,485評論 1 262
  • 我被黑心中介騙來泰國打工赁还, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留妖泄,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 45,501評論 2 354
  • 正文 我出身青樓艘策,卻偏偏與公主長得像蹈胡,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 42,792評論 2 345

推薦閱讀更多精彩內(nèi)容

  • 本文轉(zhuǎn)自美團(tuán)點(diǎn)評的[java8系列之重新認(rèn)識HashMap] (https://tech.meituan.com/...
    L千年老妖閱讀 306評論 0 0
  • HashMap是Java使用頻率很高的容器對象,內(nèi)部使用了很多優(yōu)化算法,源碼非常值得學(xué)習(xí). 關(guān)于HashMap 非...
    r09er閱讀 433評論 0 1
  • 前言 這次我和大家一起學(xué)習(xí)HashMap罚渐,HashMap我們在工作中經(jīng)常會(huì)使用却汉,而且面試中也很頻繁會(huì)問到,因?yàn)樗?..
    liangzzz閱讀 7,965評論 7 102
  • 一荷并、學(xué)習(xí)與實(shí)踐 1.付出不亞于任何人的努力 2.要謙虛合砂,不要驕傲 3.要每天反省 4.活著,就要感謝 5.積善行源织,...
    聶偉n閱讀 63評論 0 0
  • 以前聽朋友說過谈息,每個(gè)女人都有100次想離婚的念頭缘屹,無論你嫁的老公是否有錢。 為什么侠仇?我并不覺得原因很復(fù)雜……因?yàn)槔?..
    尋找幸福的熊閱讀 1,278評論 0 0