ArrayList其实就是一个长度可变的数组,初始其实是空数组,当添加第一个元素的时候数组容量才变成10
插入删除元素的时间复杂度为O(n),求表长以及增加元素,取第 i 元素的时间复杂度为O(1)
1.ArrayList的数据结构
//使用一个Object数组进行存储
transient Object[] elementData;
//数组元素的大小
private int size;
2.add方法
1.无指定下标的add方法
以下的JDK源码
//增加方法
public boolean add(E e) {
ensureCapacityInternal(size + 1); // Increments modCount!!
elementData[size++] = e;
return true;
}
//检查是否要扩容
private void ensureCapacityInternal(int minCapacity) {
ensureExplicitCapacity(calculateCapacity(elementData, minCapacity));
}
//得到最小扩容量
private static int calculateCapacity(Object[] elementData, int minCapacity) {
//返回默认容量和当前容器加1的最大值
if (elementData == DEFAULTCAPACITY_EMPTY_ELEMENTDATA) {
return Math.max(DEFAULT_CAPACITY, minCapacity);
}
return minCapacity;
}
//判断是否需要扩容
private void ensureExplicitCapacity(int minCapacity) {
modCount++;
//容量超出即扩容
if (minCapacity - elementData.length > 0)
grow(minCapacity);
}
//扩容
private void grow(int minCapacity) {
//保存旧容量
int oldCapacity = elementData.length;
//新容量为旧容量的1.5倍
int newCapacity = oldCapacity + (oldCapacity >> 1);
//新容量是否小于最小需要容量
if (newCapacity - minCapacity < 0)
newCapacity = minCapacity;
//新容量是否超出了ArrayList所定义的最大容量
if (newCapacity - MAX_ARRAY_SIZE > 0)
newCapacity = hugeCapacity(minCapacity);
//拷贝,ArrayscopyOf()继续调用System的arraycopy
elementData = Arrays.copyOf(elementData, newCapacity);
}
总结:
1、先判断是否扩容再赋值
2、扩容为原来数组的1.5倍
3、使用System的拷贝方法
2.指定下标的add方法
public void add(int index, E element) {
//检查下标是否越界
rangeCheckForAdd(index);
//判断是否要扩容
ensureCapacityInternal(size + 1);
//让index开始之后的所有成员后移一个位置:
System.arraycopy(elementData, index, elementData, index + 1,
size - index);
elementData[index] = element;
size++;
}
remove方法和get方法类似,只不过是删除元素并且左移