java集合中List,Set,Map的特點以及在工作中如何選型

2020-10-20 11:00:12

提到java的資料結構我們首先想到的肯定是集合,什麼map啦,list啦,set啦。下面我們就來說一說這些集合的特點以及特性。

所有集合的父介面:

Collection和Map是所有集合的父介面。

  • List和Set繼承至Collection介面
  • Map自己為一個獨立的介面

List介面:

  • List介面下有ArrayList,LinkedList,以及Vector

Set介面:

  • Set介面下有HashSet,LinkedHashSet,以及TreeSet

Map介面:

  • Map介面下有HashMap,LinkedHashMap,HashTable,以及TreeMap

我們可以通過下圖看出他們之間的關係。
在這裡插入圖片描述

需要注意的是不僅僅只有Set介面和List介面繼承了Collection介面,還有Queue介面也同樣繼承至Collection。

通過原始碼我們就又會發現LinkedList介面不僅實現了List介面,還實現了Deque介面,而Deque繼承至Queue,Queue介面繼承至Collection介面,錯綜複雜的關係需要閱讀原始碼才能夠了解的更透徹。

public class LinkedList<E>
    extends AbstractSequentialList<E>
    implements List<E>, Deque<E>, Cloneable, java.io.Serializable

言歸正傳,繼續我們剛才的話題,來說說這些集合各自的特點。

集合各自的特點:

List 有序。並且可重複

  • ArrayList
    優點: ArrayList的底層資料結構是陣列,查詢快但增刪慢。
    缺點: 執行緒不安全,效率高

為什麼ArrayList查詢快增刪慢?

因為ArrayList的底層資料結構是陣列,陣列在查詢過程中是首地址+(元素長度bai*下標),基於這個位置讀取相應的位元組數就可以了,所以非常快。增刪會帶來元素的移動,增加資料會向後移動,刪除資料會向前移動,所以影響效率。

  • LinkedList
    優點: LinkedList的底層資料結構是連結串列,增刪快但查詢慢。執行緒安全。
    缺點: 由於是執行緒安全的,所以效率低。

為什麼LinkedList增刪快查詢慢?

LinkedList的底層資料結構是連結串列,而連結串列存放物件是放入到一個單獨的連結(link)中,連結中還存放這下一個連結的參照,在java語言設計中連結串列都是雙向連結(Double linked)—即每個物件都還存放這前驅的參照,所以資料增刪不會移動其他元素的位置。增刪就相對陣列來說比較快。但是在查詢的時候只能通過順次指標存取,所以查詢較慢。

  • Vector
    優點: Vector的底層資料結構是陣列,查詢快但同樣增刪慢。執行緒安全。
    缺點: 由於是執行緒安全的,所以效率低。

Set 唯一

  • HashSet
    優點: List的底層資料結構是雜湊表。通過hashCode()和equals()保證了元素的唯一性。
    缺點: 無序

  • LinkedHashSet
    優點: LinkedList的底層資料結構是連結串列和雜湊表,有序。通過連結串列保證了元素的有序性,又通過雜湊表保 證了元素的唯一性。
    缺點: 由於插入是要保證元素的有序性,所以效率較HashSet低。

  • TreeSet
    優點: Vector的底層資料結構是紅黑樹,由於紅黑樹的特性所以TreeSet是有序的,並且通過比較元素的返回值是否是0來決定該元素的唯一性。

Map KV鍵值對儲存

  • HashMap
    優點: JDK1.8以後底層資料結構是陣列+連結串列+紅黑樹,鍵唯一。允許存在一個null鍵和null值。
    缺點: 執行緒不安全
  • LinkedHashMap
    優點: 繼承至HashMap,保證了元素的插入順序。
    缺點: 由於插入是要保證元素的有序性,所以效率較HashSet低。
  • HashTable HashTable底層資料結構是雜湊表,執行緒安全
    優點: 效率低
  • TreeMap 底層資料結構是紅黑樹,自然排序,
    優點: 效率較HashMap低

集合的選型

在工作中避免不了要使用集合,那麼這麼多集合型別我們到底該如何選擇呢?
這就需要根據我們的使用需求來決定了。

是否需要儲存鍵值對
——否:Set或者List
————資料是否唯一
——————是:Set
——————是否有序
————————是,用LinkedHashSet,TreeSet
————————否,用HashSet
————————如果你只知道資料要唯一但不確定是否有序,就要HashSet
——————否:List
————————是否執行緒安全
——————————是:Vector
——————————否:ArrayList,LinkedList
————————————查詢多用ArrayList
————————————增刪多用LinkedList
————————————如果你知道要用List,但不知道查詢多還是增刪多就用ArrayList
——是Map
————是否執行緒安全
——————是:HashTable
——————否:是否允許存在null鍵
————————是:HashMap
————————否:LinkedHashMap,TreeMap
————————如果你知道要用Map但不知道要用哪個就用HashMap

參考文章:https://blog.csdn.net/zhangqunshuai/article/details/80660974