在ArrayList源码中主要的两个属性是 Object数组和元素个数,
elementData 用transient修饰的原因:当数组长度为10,这时候只有5个元素,默认序列化会占用10个空间。用transient修饰后,再重写writeOjbect和readObject可以自己定义序列化逻辑,节省空间
transient Object[] elementData; private int size;
自己实现的 ArrayList, 少了很多检查,比如数组下标越界
System.arraycopy(elementData, index + 1, elementData, index, numMoved); 这是个native方法
Arrays.copyOf(elementData, newCapacity); 这个方法内部是转调System.arraycopy方法
在源码中数组扩容是增加为原来的1.5倍,扩容时候用到了>> 右移操作,就是将一个数减少一半。假如数组初始大小为1,会做额外的判断
public class MyArrayList<E> implements Iterable<E> { Object[] elementData; int size; public MyArrayList() { elementData = new Object[10]; size = 0; } public void add(Object obj) { ensureExplicitCapacity(size + 1); elementData[size++] = obj; } private void ensureExplicitCapacity(int minCapacity) { if (size == elementData.length) { // 原来本身elementData容量大小 2 int oldCapacity = elementData.length; // 新数据容量大小 (oldCapacity >> 1)=oldCapacity/ int newCapacity = oldCapacity + (oldCapacity >> 1);// (2+2/2)=3 // 如果初始容量为1的时候,那么他扩容的大小为多少呢? if (newCapacity - minCapacity < 0) newCapacity = minCapacity; // 最少保证容量和minCapacity一样 // 将老数组的值赋值到新数组里面去 elementData = Arrays.copyOf(elementData, newCapacity); } } public Object remove(int index) { Object object = get(index);// index 2 // 计算删除元素后面的长度 int numMoved = size - index - 1; // 5 // 2.删除原理 使用arraycopy往前移动数据,将最后一个变为空 if (numMoved > 0) System.arraycopy(elementData, index + 1, elementData, index, numMoved); elementData[--size] = null; // 将最后一个元素变为空 return object; } public Object get(int index) { return elementData[index]; } @Override public Iterator<E> iterator() { Iterator<E> iterator = new Iterator<E>() { int index = 0; @Override public boolean hasNext() { if (index < size) { return true; } else { return false; } } @SuppressWarnings("unchecked") @Override public E next() { return (E) elementData[index++]; } }; return iterator; } public static void main(String[] args) { MyArrayList<Integer> list = new MyArrayList<Integer>(); for (int i = 10; i < 23; i++) { list.add(i); } Iterator<Integer> iterator = list.iterator(); while (iterator.hasNext()) { System.out.print(iterator.next() + " "); } System.out.println(); System.out.println(list.get(5)); list.remove(6); Iterator<Integer> iterator2 = list.iterator(); while (iterator2.hasNext()) { System.out.print(iterator2.next() + " "); } } }