數(shù)據(jù)結(jié)構(gòu)對比(HashMap岩四,ConcurrentHashMap,HashTable哥攘,ArrayList剖煌,LinkedList)

一、概論

????這篇文章的目的只有一個(gè)就是對日常開發(fā)中遇到的一些數(shù)據(jù)結(jié)構(gòu)對其特點(diǎn)逝淹,進(jìn)行歸納總結(jié)耕姊,具體的細(xì)節(jié)再后續(xù)的文章再一一解釋。

二栅葡、特點(diǎn)分析

2.1 ArrayList
  • 基于動(dòng)態(tài)數(shù)組實(shí)現(xiàn)茉兰,當(dāng)創(chuàng)建一個(gè) ArrayList 對象時(shí),實(shí)際上是創(chuàng)建了一個(gè) Object 類型的數(shù)組欣簇,初始容量為 10
  • 當(dāng)添加元素時(shí)规脸,如果數(shù)組已滿,ArrayList 會(huì)自動(dòng)擴(kuò)容熊咽,它會(huì)創(chuàng)建一個(gè)新的數(shù)組莫鸭,并將原數(shù)組中的元素復(fù)制到新數(shù)組中。
  • 使用了快速失敗機(jī)制 (Fail-Fast)
    指的是在多線程環(huán)境下横殴,如果一個(gè)線程修改了ArrayList的結(jié)構(gòu)(增加被因、刪除或修改元素),那么其他線程在訪問ArrayList時(shí)衫仑,如果發(fā)現(xiàn)modCount屬性(記錄ArrayList結(jié)構(gòu)修改次數(shù)的屬性)與自己持有的modCount屬性不一致梨与,就會(huì)拋出ConcurrentModificationException異常,從而防止多個(gè)線程同時(shí)修改ArrayList的結(jié)構(gòu)文狱,導(dǎo)致數(shù)據(jù)不一致的情況發(fā)生粥鞋。
2.2 LinkedList
  • 優(yōu)點(diǎn):
    鏈表的主要優(yōu)點(diǎn)是在插入和刪除節(jié)點(diǎn)時(shí)具有較低的時(shí)間復(fù)雜度。因?yàn)殒湵碇械墓?jié)點(diǎn)可以在內(nèi)存中非連續(xù)地分布瞄崇,插入和刪除操作只涉及到修改指針的指向呻粹,而不需要移動(dòng)其他節(jié)點(diǎn)到踏。這使得鏈表在動(dòng)態(tài)數(shù)據(jù)結(jié)構(gòu)、頻繁的插入和刪除操作以及不需要事先知道數(shù)據(jù)大小的情況下非常有用尚猿。

  • 缺點(diǎn):
    然而窝稿,鏈表的缺點(diǎn)是訪問特定位置的節(jié)點(diǎn)需要遍歷整個(gè)鏈表,時(shí)間復(fù)雜度為O(n)凿掂。與數(shù)組相比伴榔,鏈表的隨機(jī)訪問效率較低。此外庄萎,鏈表需要額外的內(nèi)存來存儲(chǔ)指針或引用踪少。

  • LinkedList是List接口的雙向鏈表非同步實(shí)現(xiàn),并允許包括null在內(nèi)的所有元素糠涛。

  • 底層的數(shù)據(jù)結(jié)構(gòu)是基于雙向鏈表的援奢,該數(shù)據(jù)結(jié)構(gòu)我們稱為節(jié)點(diǎn)

  • 允許所有元素為null

  • 它的查找是分兩半查找,先判斷index是在鏈表的哪一半忍捡,然后再去對應(yīng)區(qū)域查找集漾,這樣最多只要遍歷鏈表的一半節(jié)點(diǎn)即可找到

鏈表的特點(diǎn)就是在指定位置插入和刪除元素的效率較高,但是查找的 效率就不如數(shù)組那么高了

2.3 HashMap

HashMap 內(nèi)部維護(hù)了一個(gè)數(shù)組砸脊,稱為哈希表具篇,每個(gè)元素都是一個(gè)鏈表的頭結(jié)點(diǎn),該鏈表被稱為桶(bucket)凌埂。當(dāng)我們向 HashMap 中添加一個(gè)元素時(shí)驱显,首先會(huì)根據(jù)該元素的鍵值(key)計(jì)算出一個(gè)哈希值(hash code),然后根據(jù)哈希值確定該元素在數(shù)組中的位置瞳抓,如果該位置上已經(jīng)存在了元素埃疫,則將該元素添加到該位置上對應(yīng)的桶中,如果該位置上沒有元素孩哑,則創(chuàng)建一個(gè)新的桶栓霜,并將該元素添加到該桶中。

在查找元素時(shí)臭笆,HashMap 會(huì)根據(jù) key 的哈希值確定其在數(shù)組中的位置叙淌,然后遍歷該位置上的鏈表秤掌,查找是否存在對應(yīng)的 key愁铺。如果存在,則返回其對應(yīng)的 value闻鉴;如果不存在茵乱,則返回 null。由于哈希值可能會(huì)發(fā)生沖突孟岛,因此同一個(gè)桶上可能會(huì)有多個(gè)元素瓶竭,需要遍歷鏈表才能找到對應(yīng)的元素督勺。

  • HashMap 是非線程安全的,因?yàn)樗皇峭降慕锓。鄠€(gè)線程同時(shí)對 HashMap 進(jìn)行操作可能會(huì)導(dǎo)致數(shù)據(jù)不一致的問題智哀。
  • HashMap的實(shí)現(xiàn)原理是通過將鍵對象的哈希碼映射到哈希表的索引位置來存儲(chǔ)和獲取值對象。當(dāng)多個(gè)鍵對象的哈希碼映射到同一個(gè)索引位置時(shí)荧恍,會(huì)使用鏈表或紅黑樹等數(shù)據(jù)結(jié)構(gòu)來解決沖突問題瓷叫。

優(yōu)點(diǎn):

  • 高效的插入、刪除和查找操作:由于使用哈希表來存儲(chǔ)鍵值對送巡,HashMap提供了快速的插入摹菠、刪除和查找操作
  • 可以存儲(chǔ)null鍵和null值:HashMap允許存儲(chǔ)null鍵和null值,這在某些場景下非常有用
  • 動(dòng)態(tài)擴(kuò)容:HashMap會(huì)根據(jù)當(dāng)前存儲(chǔ)的元素?cái)?shù)量動(dòng)態(tài)調(diào)整內(nèi)部數(shù)組的大小骗爆,以提高性能

缺點(diǎn):

  • 不保證元素的順序:HashMap不保證元素的順序次氨,如果需要有序的鍵值對集合,可以考慮使用LinkedHashMap
  • 線程不安全:HashMap是非線程安全的摘投,如果在多線程環(huán)境下使用煮寡,需要進(jìn)行額外的同步處理,或者使用線程安全的ConcurrentHashMap犀呼。
2.4 ConcurrentHashMap

ConcurrentHashMap是Java中的一種線程安全的哈希表實(shí)現(xiàn)洲押,它是HashMap的一個(gè)線程安全版本。與HashMap不同的是圆凰,ConcurrentHashMap可以在多線程環(huán)境下進(jìn)行并發(fā)操作而不需要額外的同步措施杈帐。它提供了高效的并發(fā)讀取和更新操作,并且保證了線程安全性专钉。

ConcurrentHashMap的實(shí)現(xiàn)原理是將整個(gè)哈希表分成多個(gè)小的子哈希表(稱為段)挑童,每個(gè)段都可以獨(dú)立地進(jìn)行讀寫操作。每個(gè)段內(nèi)部使用了與HashMap類似的哈希桶和鏈表(或紅黑樹)的數(shù)據(jù)結(jié)構(gòu)來存儲(chǔ)鍵值對跃须。當(dāng)多個(gè)線程同時(shí)訪問不同的段時(shí)站叼,它們可以并發(fā)地進(jìn)行讀寫操作,從而提高了并發(fā)性能菇民。

優(yōu)點(diǎn):

  • 高效的并發(fā)讀取和更新操作:ConcurrentHashMap允許多個(gè)線程同時(shí)進(jìn)行讀取和更新操作尽楔,提供了較好的并發(fā)性能。
  • 線程安全性:ConcurrentHashMap通過使用鎖分段技術(shù)來保證線程安全性第练,不需要額外的同步措施阔馋。
  • 動(dòng)態(tài)擴(kuò)容:ConcurrentHashMap可以根據(jù)需要?jiǎng)討B(tài)調(diào)整大小,以適應(yīng)不同的并發(fā)訪問情況娇掏。

缺點(diǎn):

  • 內(nèi)存占用較大:由于ConcurrentHashMap需要維護(hù)多個(gè)段擎浴,因此相對于HashMap來說联逻,它的內(nèi)存占用會(huì)更大一些。

  • 迭代性能較低:由于ConcurrentHashMap的內(nèi)部結(jié)構(gòu)是分段的歧寺,因此在迭代操作時(shí)性能可能會(huì)受到一定的影響。
    ConcurrentHashMap在實(shí)際開發(fā)中常用于需要高并發(fā)讀寫操作的場景,例如緩存、并發(fā)任務(wù)處理和并發(fā)計(jì)算等。它提供了一種線程安全的哈希表實(shí)現(xiàn)讶坯,可以有效地處理多線程環(huán)境下的并發(fā)訪問問題。

2.5 HashTable
  • Hashtable底層也采用數(shù)組+鏈表的數(shù)據(jù)結(jié)構(gòu)進(jìn)行實(shí)現(xiàn)岗屏,當(dāng)哈希沖突發(fā)生時(shí)闽巩,使用鏈表來解決沖突。與HashMap不同的是担汤,Hashtable在JDK 8及以前沒有使用紅黑樹解決哈希沖突涎跨,這導(dǎo)致了其效率相對較低。

  • Hashtable是線程安全的類崭歧,即多個(gè)線程同時(shí)操作Hashtable中的元素也不會(huì)產(chǎn)生錯(cuò)誤的結(jié)果或者拋出ConcurrentModificationException異常隅很。

  • Hashtable不允許存儲(chǔ)null值和null鍵,否則將會(huì)拋出NullPointerException異常率碾。

  • Hashtable在JDK 8及以前沒有使用紅黑樹解決哈希沖突叔营,相對于HashMap而言,Hashtable的效率比較低所宰。另外绒尊,由于Hashtable不支持null鍵和null值,因此對其進(jìn)行操作時(shí)要額外小心仔粥。Hashtable的查找婴谱、插入和刪除操作平均時(shí)間復(fù)雜度為O(1),但是在極端情況下躯泰,因?yàn)楣_突的原因谭羔,可能會(huì)退化到O(n)。











參考文獻(xiàn)
ArrayList 的底層原理和源碼分析
深入理解Array麦向、List瘟裸、Map集合框架底層實(shí)現(xiàn)原理
ArrayList的底層實(shí)現(xiàn)原理
LinkedList 的實(shí)現(xiàn)原理
LinkedList原理解析
hashmap & hashtable 區(qū)別
hashmap hashtable學(xué)習(xí)筆記
ConcurrentHashMap 底層原理
深入理解ConcurrentHashMap
深度解析Hashtable

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市诵竭,隨后出現(xiàn)的幾起案子话告,更是在濱河造成了極大的恐慌,老刑警劉巖卵慰,帶你破解...
    沈念sama閱讀 218,451評論 6 506
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件沙郭,死亡現(xiàn)場離奇詭異,居然都是意外死亡呵燕,警方通過查閱死者的電腦和手機(jī)棠绘,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,172評論 3 394
  • 文/潘曉璐 我一進(jìn)店門件相,熙熙樓的掌柜王于貴愁眉苦臉地迎上來再扭,“玉大人氧苍,你說我怎么就攤上這事》悍叮” “怎么了让虐?”我有些...
    開封第一講書人閱讀 164,782評論 0 354
  • 文/不壞的土叔 我叫張陵,是天一觀的道長罢荡。 經(jīng)常有香客問我赡突,道長,這世上最難降的妖魔是什么区赵? 我笑而不...
    開封第一講書人閱讀 58,709評論 1 294
  • 正文 為了忘掉前任惭缰,我火速辦了婚禮,結(jié)果婚禮上笼才,老公的妹妹穿的比我還像新娘漱受。我一直安慰自己,他們只是感情好骡送,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,733評論 6 392
  • 文/花漫 我一把揭開白布昂羡。 她就那樣靜靜地躺著,像睡著了一般摔踱。 火紅的嫁衣襯著肌膚如雪虐先。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,578評論 1 305
  • 那天派敷,我揣著相機(jī)與錄音蛹批,去河邊找鬼。 笑死篮愉,一個(gè)胖子當(dāng)著我的面吹牛般眉,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播潜支,決...
    沈念sama閱讀 40,320評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼甸赃,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了冗酿?” 一聲冷哼從身側(cè)響起埠对,我...
    開封第一講書人閱讀 39,241評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎裁替,沒想到半個(gè)月后项玛,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,686評論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡弱判,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,878評論 3 336
  • 正文 我和宋清朗相戀三年襟沮,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 39,992評論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡开伏,死狀恐怖膀跌,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情固灵,我是刑警寧澤捅伤,帶...
    沈念sama閱讀 35,715評論 5 346
  • 正文 年R本政府宣布,位于F島的核電站巫玻,受9級(jí)特大地震影響丛忆,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜仍秤,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,336評論 3 330
  • 文/蒙蒙 一熄诡、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧诗力,春花似錦粮彤、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,912評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至圈澈,卻和暖如春惫周,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背康栈。 一陣腳步聲響...
    開封第一講書人閱讀 33,040評論 1 270
  • 我被黑心中介騙來泰國打工递递, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人啥么。 一個(gè)月前我還...
    沈念sama閱讀 48,173評論 3 370
  • 正文 我出身青樓登舞,卻偏偏與公主長得像,于是被迫代替她去往敵國和親悬荣。 傳聞我的和親對象是個(gè)殘疾皇子菠秒,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,947評論 2 355

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