ArrayList 内部结构为一个可重复的对象数组(可存空对象)。
内部有以下几个参数:
/**
* 默认初始容量
*/
private static final int DEFAULT_CAPACITY = 10;
/**
* 用于空实例的共享空数组实例
*/
private static final Object[] EMPTY_ELEMENTDATA = {};
/**
* 存储数组列表元素的数组缓冲区。数组列表的容量是这个数组缓冲区的长度
*/
private transient Object[] elementData;
/**
* 数组列表的大小
*
* @serial
*/
private int size;
//默认数组最大值
private static final int MAX_ARRAY_SIZE = Integer.MAX_VALUE - 8;
分析几个内部方法:
1.indexOf(Object o):
public int indexOf(Object o) { if (o == null) { for (int i = 0; i < size; i++) if (elementData[i]==null) return i; } else { for (int i = 0; i < size; i++) if (o.equals(elementData[i])) return i; } return -1; }
循环对象数组进行比较,返回第一个匹配到的对象的下标,若未匹配到返回-1,提供给contains(Object o) 方法。
2.add(Object o): 添加前需要对容量进行容量检查 扩展容量。
public boolean add(E e) { ensureCapacityInternal(size + 1); // 确保内部容量: elementData[size++] = e; //添加元素 return true; }
//确保内部容量
private void ensureCapacityInternal(int minCapacity) { if (elementData == EMPTY_ELEMENTDATA) { minCapacity = Math.max(DEFAULT_CAPACITY, minCapacity); } ensureExplicitCapacity(minCapacity); }
//确保明确的容量 private void ensureExplicitCapacity(int minCapacity) { modCount++; if (minCapacity - elementData.length > 0) grow(minCapacity); }
//扩展
private void grow(int minCapacity) { int oldCapacity = elementData.length;
//扩展容量为之前容量的3/2 int newCapacity = oldCapacity + (oldCapacity >> 1); if (newCapacity - minCapacity < 0) newCapacity = minCapacity;
//如果扩展后的容量大于数组最大值,扩展至最大容量 if (newCapacity - MAX_ARRAY_SIZE > 0) newCapacity = hugeCapacity(minCapacity); // elementData = Arrays.copyOf(elementData, newCapacity); } private static int hugeCapacity(int minCapacity) { if (minCapacity < 0) // overflow throw new OutOfMemoryError();
如果最小容量大于数组最大值,则扩展至Integer的最大值否则扩展至数组默认最大值 return (minCapacity > MAX_ARRAY_SIZE) ? Integer.MAX_VALUE : MAX_ARRAY_SIZE; }
3.remove(int index):按数组下标移除对象元素,
public E remove(int index) {
//边界检查 rangeCheck(index); //修改次数+1 modCount++; E oldValue = elementData(index); int numMoved = size - index - 1; if (numMoved > 0)
//数组拷贝 System.arraycopy(elementData, index+1, elementData, index, numMoved);
//清空最后一位 elementData[--size] = null; // clear to let GC do its work return oldValue; }
4.remove(Object o):按对象移除,只移除匹配到的第一个相同对象
public boolean remove(Object o) {
//从前往后匹配,若匹配到则根据下标进行删除。 if (o == null) { for (int index = 0; index < size; index++) if (elementData[index] == null) { fastRemove(index); return true; } } else { for (int index = 0; index < size; index++) if (o.equals(elementData[index])) { fastRemove(index); return true; } } return false; }
private void fastRemove(int index) { modCount++; int numMoved = size - index - 1; if (numMoved > 0) System.arraycopy(elementData, index+1, elementData, index, numMoved); elementData[--size] = null; // clear to let GC do its work }
5.addAll(Collection<? extends E> c):将指定集合中的所有元素追加到数组的末尾
public boolean addAll(Collection<? extends E> c) { Object[] a = c.toArray(); int numNew = a.length;
//扩容 ensureCapacityInternal(size + numNew); // Increments modCount
//数组拷贝 System.arraycopy(a, 0, elementData, size, numNew); size += numNew; return numNew != 0; }
6.addAll(int index, Collection<? extends E> c):从数组的某个位置添加指定集合
public boolean addAll(int index, Collection<? extends E> c) { rangeCheckForAdd(index);
//将集合转化为对象数组 Object[] a = c.toArray(); int numNew = a.length;
//扩容 ensureCapacityInternal(size + numNew); // Increments modCount //将原数组index之后的数据拷贝至index+numNew之后 int numMoved = size - index; if (numMoved > 0) System.arraycopy(elementData, index, elementData, index + numNew, numMoved); //将指定数组添加至原数组 System.arraycopy(a, 0, elementData, index, numNew); size += numNew; return numNew != 0; }
进阶之路从此开始,路在脚下早已铺好,走与不走全看你想不想欣赏沿途的风景———————AmbitiousMice