ArrayList 的源码分析(扩容机制-JDK-10)

Arraylist的源码分析(扩容机制-JDK 10)

  1. 初始化值

    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 = {};
    存储ArrayList元素的数组缓冲区
    transient Object[] elementData; // non-private to simplify nested class access
    元素个数
    private int size;
    每次数据进行修改都会+1---主要是在一些非线程安全的时候,检测是否出现混乱
    protected transient int modCount = 0;
  2. 构造方法
    默认数组的长度为10

    public ArrayList() {
        this.elementData = DEFAULTCAPACITY_EMPTY_ELEMENTDATA;
    }

    自己定义初始化的容量

    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);
       }
    }
  3. 添加元素

    public boolean add(E e) {
      modCount++;
      将元素和数组长度、数组大小(元素的个数)传过去
      add(e, elementData, size);
      return true;
    }
    private void add(E e, Object[] elementData, int s) {
        如果元素的个数和数组的长度相等,那么就需要对数组进行扩容
        if (s == elementData.length)
              elementData = grow();
         如果不是,则将元素添加到最后(元素的最后)
         elementData[s] = e;
         并且元素个数+1
         size = s + 1;
    }
  4. 开始扩容—扩容的方法

    private Object[] grow() {
    将可允许的数组的最小容量传过去(元素个数(size+1)—因为要添加一个元素)
    return grow(size + 1);

    }

    private Object[] grow(int minCapacity) {
    调用复制的方法,在原来元素基础上增加容量
    return elementData = Arrays.copyOf(elementData,
                                       newCapacity(minCapacity));
    }
    
    private int newCapacity(int minCapacity) {
    // overflow-conscious code
    获取数组的长度(默认的或是自己定义的)
    int oldCapacity = elementData.length;
    新的容量是原容量的1.5倍
    int newCapacity = oldCapacity + (oldCapacity >> 1);
    新容量比可允许的最小容量小,那么新的容量就是可允许的最小的容量
    之所以会有这个判断,是因为我们可以自己定义初始容量,而不一定是默认的容量
    if (newCapacity - minCapacity <=  0) {
        if (elementData == DEFAULTCAPACITY_EMPTY_ELEMENTDATA)
            return Math.max(DEFAULT_CAPACITY, minCapacity);
        if (minCapacity < 0) // overflow
            throw new OutOfMemoryError();
        return minCapacity;
    }
    如果新容量大于数值的最大值,传入huge方法,
    return (newCapacity - MAX_ARRAY_SIZE <= 0)
        ? newCapacity
        : hugeCapacity(minCapacity);

    }
    可允许的最小容量是否越界,如果新容量大于数组默认的最大值,赋给它整型的最大值

    private static int hugeCapacity(int minCapacity) {
        if (minCapacity < 0) // overflow
            throw new OutOfMemoryError();
        return (minCapacity > MAX_ARRAY_SIZE)
           ? Integer.MAX_VALUE
           : MAX_ARRAY_SIZE;

    }

相关推荐