我的jdk源碼(十八):LinkedHashSet類

一、概述

    LinkedHashSet類也是集合家族中的一員,LinkedHashSet類是Set類的一個實現,具有set集合不重複的特點,同時具有可預測的迭代順序,也就是我們插入的順序。那麼具體如何實現,請看源碼解析。

二、源碼解析

    1. 類的聲明

public class LinkedHashSet<E>
    extends HashSet<E>
    implements Set<E>, Cloneable, java.io.Serializable

    LinkedHashSet類繼承自HashSet類,同時實現了Set接口、Cloneable接口以及Serializable接口,這個結構和ArrayList類的結構很相似,我們仔細分析一下:

         * 繼承HashSet類,可以自己實現父類的方法(雖然源碼裏沒有,萬一以後有呢)。

        * 實現Set接口,一是爲了增加可讀性,清晰看到實現的接口,二是降低維護成本,如果HashSet類不實現Set了,LinkedHashSet類也不受影響。

        * Cloneable接口也是克隆標記接口,表示此類可以被克隆,此類的實例可以調用clone()方法;未實現Cloneable接口的類的實例調用clone()方法會報錯,在Object類中已經定義。

        * Serializable接口是序列化標記接口,表示此類可以被序列化到內存中。目的是爲類可持久化,比如在網絡傳輸或本地存儲,爲系統的分佈和異構部署提供先決條件。

    2. 構造函數

    // 傳入容量和裝載因子
    public LinkedHashSet(int initialCapacity, float loadFactor) {
        super(initialCapacity, loadFactor, true);
    }
    
    // 只傳入容量, 裝載因子默認爲0.75
    public LinkedHashSet(int initialCapacity) {
        super(initialCapacity, .75f, true);
    }
    
    // 使用默認容量16, 默認裝載因子0.75
    public LinkedHashSet() {
        super(16, .75f, true);
    }
 
    // 將集合c中的所有元素添加到LinkedHashSet中
    // 好奇怪, 這裏計算容量的方式又變了
    // HashSet中使用的是Math.max((int) (c.size()/.75f) + 1, 16)
    // 這一點有點不得其解, 是作者偷懶?
    public LinkedHashSet(Collection<? extends E> c) {
        super(Math.max(2*c.size(), 11), .75f, true);
        addAll(c);
    }

    LinkedHashSet類所有的構造方法都是調用了HashSet的構造方法,而HashSet中又調用了LinkedHashMap類中的構造方法。源碼如下:

    //HashSet類中的構造函數
    HashSet(int initialCapacity, float loadFactor, boolean dummy) {
        map = new LinkedHashMap<>(initialCapacity, loadFactor);
    }

    //LinkedHashMap類中的構造函數
    public LinkedHashMap(int initialCapacity, float loadFactor) {
        super(initialCapacity, loadFactor);
        accessOrder = false;
    }

    這樣我們就能清晰的瞭解到,LinkedHashSet類創建的實例是遵循了LinkedHashMap中排序規則accessOrder爲false, 也就是會按照插入順序進行排序(在創建新節點的時候,把該節點放到了尾部) 。

    3. 迭代器

    // 可分割的迭代器, 主要用於多線程並行迭代處理時使用
    @Override
    public Spliterator<E> spliterator() {
        return Spliterators.spliterator(this, Spliterator.DISTINCT | Spliterator.ORDERED);
    }

三、總結

    LinkedHashSet類是我們瞭解集合大家庭族譜中的一個環節,LinkedHashSet類重要的知識點有如下幾點:

    1. LinkedHashSet的底層使用LinkedHashMap存儲元素。

    2. LinkedHashSet是有序的,它是按照插入的順序排序的,不支持按元素訪問順序排序。

    敬請期待《  我的jdk源碼(十九):TreeMap  》。

    更多精彩內容,敬請掃描下方二維碼,關注我的微信公衆號【Java覺淺】,獲取第一時間更新哦!

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章