java集合 ArrayList扩容

本文详细解析了Java中ArrayList的扩容机制,包括add()方法、内部的ensureCapacityInternal()和grow()函数,以及容量计算逻辑。特别关注了默认容量、扩容策略及复制元素过程。
摘要由CSDN通过智能技术生成

前言

在Java中,ArrayList 是一个动态数组实现,它可以根据需要自动扩容。ArrayList 扩容的机制是在容量不足时,自动增加容量并将元素复制到新的数组中。

add() 方法

 ArrayList<Integer> list = new ArrayList<>();
        list.add(1);

add()方法源码

    public boolean add(E e) {
        ensureCapacityInternal(size + 1);  // Increments modCount!!
        elementData[size++] = e;
        return true;
    }

ensureCapacityInternal(size + 1)这是一个私有方法,用于确保ArrayList内部数组的容量足够来容纳至少指定数量的元素。size + 1表示添加一个元素后的预期大小。如果内部数组的容量不够,该方法会触发扩容操作

    private void ensureCapacityInternal(int minCapacity) {
        ensureExplicitCapacity(calculateCapacity(elementData, minCapacity));
    }

    private void ensureExplicitCapacity(int minCapacity) {
        modCount++;

        // 触发扩容
        if (minCapacity - elementData.length > 0)
            grow(minCapacity);
    }

    private static int calculateCapacity(Object[] elementData, int minCapacity) {
        if (elementData == DEFAULTCAPACITY_EMPTY_ELEMENTDATA) {
            return Math.max(DEFAULT_CAPACITY, minCapacity);
        }
        return minCapacity;
    }

ensureCapacityInternal(int minCapacity) 方法:这个方法用于确保 ArrayList 内部数组的容量足够大,以容纳至少 minCapacity 个元素。它会调用 ensureExplicitCapacity() 方法来实现这一目标。

calculateCapacity(Object[] elementData, int minCapacity) 方法作用
首先,它检查 elementData 是否等于 DEFAULTCAPACITY_EMPTY_ELEMENTDATA【表示新建数组,还没添加元素】

  1. 如果创建数组没有指定数组大小ArrayList<Integer> list = new ArrayList<>();则会返回默认值(默认容量DEFAULT_CAPACITY大小为10)
  2. 否则返回自己创建时指定的大小,例如: ArrayList<Integer> list = new ArrayList<>(20);则返回20
    在这里插入图片描述

ensureExplicitCapacity(int minCapacity) 方法:这个方法是实际执行扩容操作的地方。它首先增加了 modCount,这是一个用于记录修改次数的计数器。然后,它检查当前容量是否足够,如果不足,就会调用 grow(minCapacity) 方法进行扩容。

grow(int minCapacity) 方法:这个方法负责实际的扩容操作。它会创建一个新的数组,并将原有数组中的元素复制到新的数组中。新数组的大小通常是原数组大小的1.5倍(也就是原数组大小加上原数组大小的一半) 。

    private void grow(int minCapacity) {
       // overflow-conscious code
       int oldCapacity = elementData.length;
       int newCapacity = oldCapacity + (oldCapacity >> 1);
       if (newCapacity - minCapacity < 0)
           newCapacity = minCapacity;
       if (newCapacity - MAX_ARRAY_SIZE > 0)
           newCapacity = hugeCapacity(minCapacity);
       // minCapacity is usually close to size, so this is a win:
       elementData = Arrays.copyOf(elementData, newCapacity);
   }

其中int newCapacity = oldCapacity + (oldCapacity >> 1);就表示扩容的新容量为原来容量的1.5倍 (oldCapacity >> 1)二进制中右移一位,表示除以2

小结

ArrayList的默认容量是10 。默认情况下,ArrayList的扩容策略是每次扩容增加当前容量的一半,即增加50%。当需要扩容时,ArrayList会创建一个新的容量更大的数组,并将原始数组中的元素复制到新数组中。


感谢观看,欢迎指点。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值