1. 程式人生 > >Collection 集合 及 Map 總結

Collection 集合 及 Map 總結

Collection:

各自的原理、特點及區別都在圖中有相應的體現。

Map:

1)、HashMap是基於雜湊表的Map介面的非同步實現。在JAVA程式設計中,最基本的結構就是兩種。一個是陣列,另一個是模擬指標(引用),所有的資料結構都可以用這兩個基本結構來構造的,HashMap也不例外。HashMap實際上是一個“連結串列陣列”的資料結構,每個元素存放連結串列節點的陣列,即陣列和連結串列的結合體。HashMap底層就是一個數組結構,陣列中的每一項又是一個連結串列。當新建一個HashMap的時候,就會初始化一個數組。Entry就是陣列中的元素,每個Map.Entry其實就是一個key-value對,它持有一個向下元素的引用,這就構成了連結串列。

2)、HashMap的儲存。當我們往HashMap中put元素的時候,先根據key的hashCode會重新計算hash值,根據hash值得到這個元素在陣列中的位置(即下標),如果陣列該位置上已經存放又其他元素了,那麼這個位置上的元素將以連結串列的形式存放,新加入的放在連結串列頭,最先加入的放在鏈尾。如果陣列在該位置上沒有元素,就直接將該元素放到此陣列中的該位置上。

3)、HashMap的讀取。從HashMap中get元素時,首先計算key的hashCode,找到陣列中對應位置的某一元素,然後通過key的eques方法在該位置的連結串列中找到需要的元素。

4)、HashMap中的resize(rehash)。當HashMap中的元素越來越多的時候,hash衝突的機率也就越來越高,因為陣列的長度是固定的。所以為了提高查詢的效率,就要對HahsMap的陣列進行擴容,陣列擴容這個操作也會出現在ArrayList中。這是一個常用的操作,而在HashMap陣列擴容之後,最消耗效能的點就出現了:陣列中的資料必須重新計算在新陣列中的位置,並放進去,這就是resize。那麼HashMap 什麼時候進行擴容呢?當HashMap中的元素個數超過陣列大小*loadFactor時就會進行陣列擴容,loadFactor預設值時 0.75,這是一個折中的值。也就是說預設情況下陣列大小為16,那麼當HashaMap中元素個數超過 16*0.75=12 (臨界值)的時候,就把這個陣列的大小擴充套件為2*32,即擴大一倍,然後重新計算每個元素在陣列中的位置,而這是一個非常消耗效能的操作,所以我們如果已經預知HashMap中的個數,那麼預設元素的個數能搞有效的提高HashMap的效能。

5)、與HashTable的區別:HahsMap沒有排序,允許一個null鍵和多個null值,而Hashatable不允許。HashMap把Hashtable的contains方法去掉了,改成containsvalue和containsKey,因為contains方法容易讓人引起誤解。Hashtable繼承自Dictionary類,HashMap是java1.2引進的Map介面的實現。Hashtable的方法是執行緒安全的,而HashMap不是,在多個執行緒訪問Hashtable時,不需要自己為它的方法實現同步,而HashMap就必須為之提供外同步。Hashtable和HashMap採用的has/rehash演算法大致一樣,所以效能不會有很大差異。