ArrayList 源碼(基於Java1.8)
阿新 • • 發佈:2017-10-31
dex extends code ray ati 沒有 cloneabl 刪除 class
ArrayList 基於數組實現,也就是類對變量 Object[]系列操作,封裝為常用的add,remove,indexOf, contains本質是通過 size 計數器對數組進行系列的操作實現
add 方法和 toArray 也是借助 Arrays 工具類完成
還有很有意思的地方就是add的擴容方法 ensureCapacityInternal() 就會增加50%容量,
因為底層數組是不可變的,所以add實際上是通過Arrays工具再拷貝擴容後長度的數組,然後覆蓋當前數組
預設集合長度是最優的操作,今天看源碼才明白原理,ArrayList默認構造器為內部數組定義的長度為10,當list超出指定集合的時候,ArrayList會操作自動擴容,
擴容的方法是使用Arrays.copyOf方法重新構造新的數組,然後將舊數組的數據全部拷貝到新的數組裏面,重新生成,再拷貝數組,消耗是巨大的,這也導致了 ArrayList 天生的缺點,插入刪除元素慢
public class ArrayList<E> extends AbstractList<E> implements List<E>, RandomAccess, Cloneable, java.io.Serializable { private static final long serialVersionUID = 8683452581122892189L; private static final int DEFAULT_CAPACITY = 10; private static final Object[] EMPTY_ELEMENTDATA = {}; private static final Object[] DEFAULTCAPACITY_EMPTY_ELEMENTDATA = {}; transient Object[] elementData; // non-private to simplify nested class access private int size;
源碼中可以看到,ArrayList繼承抽象類AbstractList,實現List接口,RandomAccess, Cloneable, Serializable等接口主要用於標識,並沒有很大作用
DEFAULT_CAPACITY = 10 是集合的默認初始化長度,我們常用new ArrayList<>()構造,其實就是創建一個長度為10的Object[]數組
size 為計數器,記錄當前數組的長度
public ArrayList(int initialCapacity) { if (initialCapacity > 0) { this.elementData = new Object[initialCapacity]; } else if (initialCapacity == 0) { this.elementData = EMPTY_ELEMENTDATA; } else { throw new IllegalArgumentException("Illegal Capacity: "+ initialCapacity); } } /** * Constructs an empty list with an initial capacity of ten. */ public ArrayList() { this.elementData = DEFAULTCAPACITY_EMPTY_ELEMENTDATA; }
ArrayList 源碼(基於Java1.8)