java源码解读之ArrayList------jdk 1.7

1.定义
首先看看顶级接口Collection的定义,

public interface Collection<E> extends Iterable<E> {
    //获得size
    int size();
    //size是否为0
    boolean isEmpty();
    //是否包含传入的对象
    boolean contains(Object o);
    //获得迭代器
    Iterator<E> iterator();
    //转为数组
    Object[] toArray();
    //若a不为空则把list传入a
    <T> T[] toArray(T[] a);
    //添加元素
    boolean add(E e);
    //删除元素
    boolean remove(Object o);
    //是否包含传入集合
    boolean containsAll(Collection<?> c);
    //获得并集
    boolean addAll(Collection<? extends E> c);
    //获得差集
    boolean removeAll(Collection<?> c);
    //获得交集
    boolean retainAll(Collection<?> c);
    //清空集合
    void clear();
    //判断对象是否相等
    boolean equals(Object o);
    //获得hash后的值
    int hashCode();
}

然后看看list接口

public abstract interface List<E> extends Collection<E>
{
  int size();
  boolean isEmpty();
  boolean contains(Object o);
  Iterator<E> iterator();
  Object[] toArray();
  <T> T[] toArray(T[] a);
  boolean add(E e);
  boolean remove(Object o);
  boolean containsAll(Collection<?> c);
  boolean addAll(Collection<? extends E> c);
  boolean addAll(int index, Collection<? extends E> c);
  boolean removeAll(Collection<?> c);
  boolean retainAll(Collection<?> c);
  void clear();
  boolean equals(Object o);
  int hashCode();
  //以上与Collection接口基本一致
  //获得指定位置的对象
  E get(int index);
  //对指定位置的对象重新赋值
  E set(int index, E element);
  //把paramE添加到指定位置
  void add(int index, E element);
  //删除指定位置的对象
  E remove(int index);
  //获得对象的位置
  int indexOf(Object o);
  //获得对象在集合的最后出现的位置
  int lastIndexOf(Object o);
  //还是迭代器,只是多封装了一些方法
  ListIterator<E> listIterator();
  //获得从指定位置开始的迭代器
  ListIterator<E> listIterator(int index);
  //获得指定范围的list
  List<E> subList(int fromIndex, int toIndex);
}

最后看看ArrayList的定义

public class ArrayList<E> extends AbstractList<E>
        implements List<E>, RandomAccess, Cloneable, java.io.Serializable

继承于AbstractList(是个封装实现了对list操作的抽象类)并且实现了list接口,RandomAccess(表明支持快速随机访问),
Cloneable(支持clone对象),Serializable(支持序列化);

2.属性

//序列化id
private static final long serialVersionUID = 8683452581122892189L;
//默认空间大小
private static final int DEFAULT_CAPACITY = 10;
//当调用无参构造时给个全空
private static final Object[] EMPTY_ELEMENTDATA = {};
//用于保存数据的数组
private transient Object[] elementData;
//总共拥有多少元素
private int size;
//最多可以拥有的元素
private static final int MAX_ARRAY_SIZE = Integer.MAX_VALUE 8;

3.构造器

//创建默认10大小的list
ArrayList()
//创建指定大小的list
ArrayList(int initialCapacity)
//创建与传入集合一样大小和元素的list
ArrayList(Collection<? extends E> c)

4.解析部分方法源码

4.1 增加方法
public boolean add(E e) {
        // 检查size+1是否超过设置的容量,如果超过扩容1.5倍
        ensureCapacityInternal(size + 1);
        //设置elementData数组对应位置值为传入对象
        elementData[size++] = e;
        return true;
}
public void add(int index, E element) {
        //检查传入的index是否超出size或者小于0
        rangeCheckForAdd(index);
        //判断是否需要扩容,修改次数+1
        ensureCapacityInternal(size + 1);
        //实现数组之间复制的一种方法(elementData:源数组,index:源数组要复制的起始位置,elementData:目的数组,index + 1:目的数组放置的起始位置,size index:复制的长度,源数组与目的数组都必须是同类型或者可以进行转换类型的数组)
        System.arraycopy(elementData, index, elementData, index + 1,size index);
        //设置elementData数组对应位置值为传入对象
        elementData[index] = element;
        //size+1
        size++;
}
4.2 删除方法
public E remove(int index) {
    //检查index是否大于等于size或者小于0
    rangeCheck(index);
    //修改次数+1
    modCount++;
    //需要删除元素的值
    E oldValue = elementData(index);
    //计算数组复制的位置,arraycopy需要用到
    int numMoved = size - index - 1;
    //判断计算后的值是否正常
    if (numMoved > 0)
        //把删除位置后面的数组向前移动一个位置
        System.arraycopy(elementData, index+1, elementData, index,numMoved);
        //把删除对象赋值为null(让垃圾回收尽快处理:不确定是不是这样)
        elementData[--size] = null;
        //返回删除对象
        return oldValue;
    }
}
public boolean remove(Object o) {
    //判断是否为null,若为null特殊处理
    if (o == null) {
        //循环查找null值
        for (int index = 0; index < size; index++)
            if (elementData[index] == null) {
                //删除对应位置的元素
                fastRemove(index);
                return true;
            }
    } else {
        for (int index = 0; index < size; index++)
            //若不为null,用equals方法查找到对应对象并且删除(注意这里不用==,想一下原因)
            if (o.equals(elementData[index])) {
                fastRemove(index);
                return true;
            }
    }
    return false;
}
private void fastRemove(int index) {
    //与remove(int index)基本一致,不清楚为什么还要再写一次类似的
    modCount++;
    int numMoved = size - index - 1;
    if (numMoved > 0)
        System.arraycopy(elementData, index+1, elementData, index,numMoved);
    elementData[--size] = null;
}
4.3 修改方法
public E set(int index, E element) {
    //检查index是否大于等于size或者小于0
    rangeCheck(index);
    //返回原来元素的值
    E oldValue = elementData(index);
    //把指定位置的元素改为传入值
    elementData[index] = element;
    return oldValue;
}
4.4 查找方法
public E get(int index) {
    //检查index是否大于等于size或者小于0
    rangeCheck(index);
    //返回指定位置的元素
    return elementData(index);
}
4.5 截取list方法
public List<E> subList(int fromIndex, int toIndex) {
    //判断传入参数是否符合要求
    subListRangeCheck(fromIndex, toIndex, size);
    //创建一个内部类SubList,这只是一个引用修改与删除都会对原list造成影响,截取的范围是fromIndex<=和<toIndex
    return new SubList(this, 0, fromIndex, toIndex);
}

//简单说下SubList构造器与get方法,其他方法原理类似list
SubList(AbstractList<E> parent,
        int offset, int fromIndex, int toIndex) {
    this.parent = parent;
    this.parentOffset = fromIndex;
    this.offset = offset + fromIndex;
    this.size = toIndex - fromIndex;
    this.modCount = ArrayList.this.modCount;
}
public E get(int index) {
    //检查index是否大于等于size或者小于0
    rangeCheck(index);
    //检查修改次数是否与原parent的list一致
    checkForComodification();
    //返回index+偏移量对应的元素
    return ArrayList.this.elementData(offset + index);
}
4.6 迭代器方法
//一个实现接口的迭代器方法
public Iterator<E> iterator() {
    //返回一个内部类
    return new Itr();
}
//itr迭代器中的常用方法
int cursor;
public boolean hasNext() {
    //cursor从0开始
    return cursor != size;
}
public E next() {
    //检查迭代的过程中是否有修改
    checkForComodification();
    //赋值cursor给i
    int i = cursor;
    if (i >= size)
        throw new NoSuchElementException();
    Object[] elementData = ArrayList.this.elementData;
    if (i >= elementData.length)
        throw new ConcurrentModificationException();
    cursor = i + 1;
    //返回下一个元素
    return (E) elementData[lastRet = i];
}

//arraylist自己定义的迭代器,区别在于这个迭代器还可以向上遍历
public ListIterator<E> listIterator(int index) {
    if (index < 0 || index > size)
        throw new IndexOutOfBoundsException("Index: "+index);
    return new ListItr(index);
}
public ListIterator<E> listIterator() {
    return new ListItr(0);
}
public E previous() {
    //检查迭代的过程中是否有修改
    checkForComodification();
    //把指针向上移动一格
    int i = cursor - 1;
    if (i < 0)
        throw new NoSuchElementException();
    Object[] elementData = ArrayList.this.elementData;
    if (i >= elementData.length)
        throw new ConcurrentModificationException();
    cursor = i;
    //返回上一个元素
    return (E) elementData[lastRet = i];
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值