jdk 1.8 arraylist源码解读

来源:互联网 发布:工业控制软件系统 编辑:程序博客网 时间:2024/05/18 01:30
package java.util;

import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import java.util.AbstractList;
import java.util.Arrays;
import java.util.BitSet;
import java.util.Collection;
import java.util.Comparator;
import java.util.ConcurrentModificationException;
import java.util.Iterator;
import java.util.List;
import java.util.ListIterator;
import java.util.Objects;
import java.util.RandomAccess;
import java.util.Spliterator;import java.util.ArrayList.1;
import java.util.ArrayList.ArrayListSpliterator;
import java.util.ArrayList.Itr;
import java.util.ArrayList.ListItr;
import java.util.ArrayList.SubList;
import java.util.function.Consumer;
import java.util.function.Predicate;
import java.util.function.UnaryOperator;
/**
**
*jdk 1.8
*/                                                                    标记接口      复制接口   序列化
public class ArrayList<E> extends AbstractList<E> implements List<E>, RandomAccess, Cloneable, Serializable {
    private static final long serialVersionUID = 8683452581122892189L;
    //默认大小,
    private static final int DEFAULT_CAPACITY = 10;
    //空对象数组
    private static final Object[] EMPTY_ELEMENTDATA = new Object[0];
    //默认容器空数组
    private static final Object[] DEFAULTCAPACITY_EMPTY_ELEMENTDATA = new Object[0];
    //存放数据的数组
    transient Object[] elementData;
    //元素的大小
    private int size;
    //最大的数组大小
    private static final int MAX_ARRAY_SIZE = 2147483639;

    
    
    ///构造函数
    public ArrayList(int arg0) {
        if (arg0 > 0) {
            this.elementData = new Object[arg0];
        } else {
            if (arg0 != 0) {//元素不为0
                throw new IllegalArgumentException("Illegal Capacity: " + arg0);
            }

            this.elementData = EMPTY_ELEMENTDATA;//元素为0
        }

    }
   //构造函数空数组
    public ArrayList() {
        this.elementData = DEFAULTCAPACITY_EMPTY_ELEMENTDATA;//空数组
    }
 ///构造函数 数组初始化
    public ArrayList(Collection<? extends E> arg0) {
        this.elementData = arg0.toArray(); 抽取数组
        if ((this.size = this.elementData.length) != 0) { //加入的数组长度不为0 将抽取长度赋予计算的长度size  (为了保证不会出现0值)
            if (this.elementData.getClass() != Object[].class) { //如果是一维数组
                this.elementData = Arrays.copyOf(this.elementData, this.size, Object[].class); //将数组赋予存放的数组
            }
        } else {
            this.elementData = EMPTY_ELEMENTDATA; //加入的数组为0,取默认的空
        }

    }
 
 
 
 
 
 
 //清空//
    public void trimToSize() {
        ++this.modCount; //修改的次数加一
        if (this.size < this.elementData.length) {  //如果计算的大小小于实际大小长的
            this.elementData = this.size == 0 ? EMPTY_ELEMENTDATA : Arrays.copyOf(this.elementData, this.size);
        } ///计算的大小是否0 为0取默认数组,不是截取计算的大小给实际大小,换句话说,即是把实际数组的多余的去掉

    }
   ///确保元素有新元素存放新值    容量
   /**
   *因为下个方法涉及到下面的好几个方法,所以总结下
   *当现在的数组为空的时候,要求的值大于10,取10,当小于10,不予处理
   *当现有的数组不为空的时候,要求的值小于已有长度,不予处理,要求的值大于已有长度,
   *对先有的长度进行1.5倍扩容,如果扩容后的长度大于要求长度,
   *不予考虑,如果扩容后的长度不大于要求的长度,则取要求的长度,
   *如果最后扩容大于integer.max/2 ,当要求值大于一半,取最大,小于一半,取一半
   */
    public void ensureCapacity(int arg0) {
        int arg1 = this.elementData != DEFAULTCAPACITY_EMPTY_ELEMENTDATA ? 0 : 10; ///1.当实际的数组不是空数组 arg1为0 是null取10
        if (arg0 > arg1) { 1.当前的数组不是空数组 取0 输入的值大于0   2.当前的数组为空取10  当输入的值大于10   (3.当前为null,输入值小于10 不予处理)
            this.ensureExplicitCapacity(arg0);  // 1.有值输入数大于0  2.无值输入数大于10
        }

    }
//对有值和无值进行判断
    private void ensureCapacityInternal(int arg0) {    
        if (this.elementData == DEFAULTCAPACITY_EMPTY_ELEMENTDATA) { /// 2.无值输入数大于10
            arg0 = Math.max(10, arg0); //取最大
        }

        this.ensureExplicitCapacity(arg0); //1.有值输入数大于0
    }
  ///对有值要求大于0处理
    private void ensureExplicitCapacity(int arg0) {
        ++this.modCount; //改变加一
        if (arg0 - this.elementData.length > 0) { //如果要求大小大于实际大小(若要求大小小于实际大小,不管)
            this.grow(arg0);//扩如
        }

    }
//扩容机制:如果扩容后的大小比要求的大小大,不处理,扩容后大小还小于要求大小,取要求大小,最后对大小判断,
    private void grow(int arg0) {
        int arg1 = this.elementData.length;
        int arg2 = arg1 + (arg1 >> 1);扩容之后的大小是一前的1.5倍 10的1.5倍为15
        if (arg2 - arg0 < 0) { //扩容后的大小比要求大小小
            arg2 = arg0; //把要求大小的赋予新的大小
        }
       ///arg2扩容之后比要求大,和要求大小(扩容后大小比要求大小小的代表)
        if (arg2 - 2147483639 > 0) { //扩容后大小和要求大小大于max/2 (小于一半不处理)
            arg2 = hugeCapacity(arg0); //da容量判断
        }

        this.elementData = Arrays.copyOf(this.elementData, arg2); //扩容后的或要求的新数组
    }
///最大容量判断
    private static int hugeCapacity(int arg) {
        if (arg < 0) {
            throw new OutOfMemoryError();
        } else {
            return arg > 2147483639 ? Integer.MAX_VALUE : 2147483639; //如果大于一半,取最大,如果,比整数的一半小就取一半
        }
    }

    
    
    
    
    
    ///计算的大小
    public int size() {
        return this.size;
    }
//清空
    public boolean isEmpty() {
        return this.size == 0;
    }
//是否包含没有找到,返回null
    public boolean contains(Object arg0) {
        return this.indexOf(arg0) >= 0;
    }
 ///查找下标,
    public int indexOf(Object arg0) {
        int arg1;
        if (arg0 == null) {//如果为null找到null的下标,这里可以看出arraylist放null只从小到大找出第一个null
            for (arg1 = 0; arg1 < this.size; ++arg1) {
                if (this.elementData[arg1] == null) {
                    return arg1;
                }
            }
        } else { //不为null时候
            for (arg1 = 0; arg1 < this.size; ++arg1) {
                if (arg0.equals(this.elementData[arg1])) {
                    return arg1;
                }
            }
        }

        return -1;
    }
 
 //从后向前查找,
    public int lastIndexOf(Object arg0) {
        int arg1;
        if (arg0 == null) { //为null,查出最后个null
            for (arg1 = this.size - 1; arg1 >= 0; --arg1) {
                if (this.elementData[arg1] == null) {
                    return arg1;
                }
            }
        } else { //查出最后个值的下标
            for (arg1 = this.size - 1; arg1 >= 0; --arg1) {
                if (arg0.equals(this.elementData[arg1])) {
                    return arg1;
                }
            }
        }

        return -1;
    }
 
 
 
  //复制接口
    public Object clone() {
        try {
            ArrayList arg0 = (ArrayList) super.clone(); ///创建新的arraylist 相当于new +copy
            arg0.elementData = Arrays.copyOf(this.elementData, this.size); //装入数据
            arg0.modCount = 0; //改变次数为0
            return arg0; 返回
        } catch (CloneNotSupportedException arg1) {
            throw new InternalError(arg1); //复制失败
        }
    }
//集合转换成数组,
    public Object[] toArray() {
        return Arrays.copyOf(this.elementData, this.size);
    }
//如果输入的数组大于list,将list会覆盖输入数组的list长度数组,否则,返回list的数组
    public <T> T[] toArray(T[] arg0) {
        if (arg0.length < this.size) { 如果输入的数组的长度小于现有的长度
            return (Object[]) Arrays.copyOf(this.elementData, this.size, arg0.getClass()); //返回现有的长度的数组
        } else {//输入的长度大于等于现有的长度
            System.arraycopy(this.elementData, 0, arg0, 0, this.size); 把现有的长度放在要求的数组的0开始的位置
            if (arg0.length > this.size) {
                arg0[this.size] = null; //要求的长度大于先有的长度,把输入的数组的长度的下标是现有的长度的下标符为null
            }

            return arg0; //返回输入
        }
    }
//返回下标元素
    E elementData(int arg0) {
        return this.elementData[arg0];
    }
//获取下标元素
    public E get(int arg0) {
        this.rangeCheck(arg0);//检查范围要求 下标在范围内
        return this.elementData(arg0);
    }
//设置下标元素,返回旧值
    public E set(int arg0, E arg1) {
        this.rangeCheck(arg0);//小于size(不包含)
        Object arg2 = this.elementData(arg0);
        this.elementData[arg0] = arg1;
        return arg2;
    }
//1.数组扩容,尾加入元素
    public boolean add(E arg0) {
        this.ensureCapacityInternal(this.size + 1);//初始化数组容器范围
        this.elementData[this.size++] = arg0;//在数组最后加入元素
        return true;
    }
///1.一,检查范围,二,扩容,三,复制 四,加入 把后半数整体后移(包含以前在这个下标的数)
    public void add(int arg0, E arg1) {
        this.rangeCheckForAdd(arg0);//检查范围 1-size 包含
        this.ensureCapacityInternal(this.size + 1);
        System.arraycopy(this.elementData, arg0, this.elementData, arg0 + 1, this.size - arg0);
                                 目标数组 开始位值     当前数组   添加的下一位   从开始的数,到最后个数,即是后半部分复制的个数(包含当前位置)
        this.elementData[arg0] = arg1; //加入要加入的数
        ++this.size;//计算的大小加一
    }
//移除
    public E remove(int arg0) {
        this.rangeCheck(arg0);//检查范围
        ++this.modCount; //改变次数加一
        Object arg1 = this.elementData(arg0); //获取当前次数
        int arg2 = this.size - arg0 - 1; //最后下标减当前下标 剩余元素的个数(不包含当前位置的值)
        if (arg2 > 0) { //
            System.arraycopy(this.elementData, arg0 + 1, this.elementData, arg0, arg2);//数组重组
                                                   下一位  目标数组               
        }

        this.elementData[--this.size] = null; //数组的最后位为null
        return arg1;//返回移除的值
    }
//从前向后,移除第一个元素
    public boolean remove(Object arg0) {
        int arg1;
        if (arg0 == null) { //输入的数是否为null
            for (arg1 = 0; arg1 < this.size; ++arg1) {
                if (this.elementData[arg1] == null) { //查找数组元素是否为null
                    this.fastRemove(arg1); //移除,并重组数组
                    return true; //第一个元素null移除
                }
            }
        } else { //不为null
            for (arg1 = 0; arg1 < this.size; ++arg1) {
                if (arg0.equals(this.elementData[arg1])) { //是否相等
                    this.fastRemove(arg1);
                    return true;
                }
            }
        }

        return false;
    }
//移除,重组数组
    private void fastRemove(int arg0) {
        ++this.modCount; //改变的次数加一
        int arg1 = this.size - arg0 - 1; //剩余元素
        if (arg1 > 0) { //还有
            System.arraycopy(this.elementData, arg0 + 1, this.elementData, arg0, arg1); //重组
        }

        this.elementData[--this.size] = null; //最后位置null
    }
//清空
    public void clear() {
        ++this.modCount; //改变次数加一

        for (int arg0 = 0; arg0 < this.size; ++arg0) {
            this.elementData[arg0] = null; //把所有元素清空
        }

        this.size = 0;
    }
 //添加集合 返回添加的集合大小是否为0的判断
    public boolean addAll(Collection<? extends E> arg0) {
        Object[] arg1 = arg0.toArray(); //变成数组
        int arg2 = arg1.length;//加入的集合大小
        this.ensureCapacityInternal(this.size + arg2); //对数组容器进行处理
        System.arraycopy(arg1, 0, this.elementData, this.size, arg2);//加入到数组的末尾
        this.size += arg2; //计算大小进行增加
        return arg2 != 0;
    }
//在特定的地址上添加元素
    public boolean addAll(int arg0, Collection<? extends E> arg1) {
        this.rangeCheckForAdd(arg0); //确定范围
        Object[] arg2 = arg1.toArray();//转化成数组
        int arg3 = arg2.length;//得到要转化的数组
        this.ensureCapacityInternal(this.size + arg3);//初始化容器
        int arg4 = this.size - arg0; 剩余元素
        if (arg4 > 0) {
            System.arraycopy(this.elementData, arg0, this.elementData, arg0 + arg3, arg4);数组的搬运,把要加入的元素的后面的部分向后搬
        }

        System.arraycopy(arg2, 0, this.elementData, arg0, arg3); //把要加入的数组放在加入的位置
        this.size += arg3; //数组增加相应的长度
        return arg3 != 0; //判断加入的长度是否为0
    }
//移除相应的长度    ,返回现有的长度  删掉      没删掉
    protected void removeRange(int arg0, int arg1) {
        ++this.modCount;//改变的次数加一
        int arg2 = this.size - arg1;//最后个元素到arg1的元素个数
        System.arraycopy(this.elementData, arg1, this.elementData, arg0, arg2);
        int arg3 = this.size - (arg1 - arg0); //现有的长度

        for (int arg4 = arg3; arg4 < this.size; ++arg4) {  
            this.elementData[arg4] = null;//最后的数组置null
        }

        this.size = arg3;//
    }
//检查,要求,范围在下标
    private void rangeCheck(int arg0) {
        if (arg0 >= this.size) {
            throw new IndexOutOfBoundsException(this.outOfBoundsMsg(arg0));
        }
    }
//检查 范围0到size包含
    private void rangeCheckForAdd(int arg0) {
        if (arg0 > this.size || arg0 < 0) {
            throw new IndexOutOfBoundsException(this.outOfBoundsMsg(arg0));
        }
    }
//错误提示
    private String outOfBoundsMsg(int arg0) {
        return "Index: " + arg0 + ", Size: " + this.size;
    }
//移除共有元素(arg0实例化对象arraylist)
    public boolean removeAll(Collection<?> arg0) {
        Objects.requireNonNull(arg0); //objects的工具,不为null返回原值
        return this.batchRemove(arg0, false);
    }
//保留输入数组和list中的重合元素
    public boolean retainAll(Collection<?> arg0) {
        Objects.requireNonNull(arg0);
        return this.batchRemove(arg0, true);
    }
//批量删除
    private boolean batchRemove(Collection<?> arg0, boolean arg1) {
        Object[] arg2 = this.elementData;//现有的数组
        int arg3 = 0;
        int arg4 = 0;
        boolean arg5 = false;

        while (true) {
            boolean arg10 = false;//标记位

            try {
                arg10 = true;
                if (arg3 >= this.size) { //变量3大于现有的长度
                    arg10 = false;//标记位置false
                    break;  ///跳出循环
                }

                if (arg0.contains(arg2[arg3]) == arg1) {
                    arg2[arg4++] = arg2[arg3];
                }

                ++arg3;
            } finally {
                if (arg10) {
                    if (arg3 != this.size) {
                        System.arraycopy(arg2, arg3, arg2, arg4, this.size - arg3);
                        arg4 += this.size - arg3;
                    }

                    if (arg4 != this.size) {
                        for (int arg8 = arg4; arg8 < this.size; ++arg8) {
                            arg2[arg8] = null;
                        }

                        this.modCount += this.size - arg4;
                        this.size = arg4;
                        arg5 = true;
                    }

                }
            }
        }

        if (arg3 != this.size) {
            System.arraycopy(arg2, arg3, arg2, arg4, this.size - arg3);
            arg4 += this.size - arg3;
        }

        if (arg4 != this.size) {
            for (int arg6 = arg4; arg6 < this.size; ++arg6) {
                arg2[arg6] = null;
            }

            this.modCount += this.size - arg4;
            this.size = arg4;
            arg5 = true;
        }

        return arg5;
    }
///写对象,序列化
    private void writeObject(ObjectOutputStream arg0) throws IOException {
        int arg1 = this.modCount;
        arg0.defaultWriteObject();
        arg0.writeInt(this.size); //写出大小

        for (int arg2 = 0; arg2 < this.size; ++arg2) {
            arg0.writeObject(this.elementData[arg2]);写入
        }

        if (this.modCount != arg1) {
            throw new ConcurrentModificationException();
        }
    }
//读
    private void readObject(ObjectInputStream arg0) throws IOException, ClassNotFoundException {
        this.elementData = EMPTY_ELEMENTDATA;
        arg0.defaultReadObject();
        arg0.readInt();
        if (this.size > 0) {
            this.ensureCapacityInternal(this.size);//初始化容量
            Object[] arg1 = this.elementData;

            for (int arg2 = 0; arg2 < this.size; ++arg2) {
                arg1[arg2] = arg0.readObject(); //读入(迭代)
            }
        }

    }
///创建一个(一定容量)迭代器
    public ListIterator<E> listIterator(int arg0) {
        if (arg0 >= 0 && arg0 <= this.size) {
            return new ListItr(this, arg0);
        } else {
            throw new IndexOutOfBoundsException("Index: " + arg0);
        }
    }
 ///返回跌带器,模式fail-fast
    public ListIterator<E> listIterator() {
        return new ListItr(this, 0);
    }

    public Iterator<E> iterator() {
      return new Itr(this, (1)null);
   }

    public List<E> subList(int arg0, int arg1) {
        subListRangeCheck(arg0, arg1, this.size);
        return new SubList(this, this, 0, arg0, arg1);
    }

    static void subListRangeCheck(int arg, int arg0, int arg1) {
        if (arg < 0) {
            throw new IndexOutOfBoundsException("fromIndex = " + arg);
        } else if (arg0 > arg1) {
            throw new IndexOutOfBoundsException("toIndex = " + arg0);
        } else if (arg > arg0) {
            throw new IllegalArgumentException("fromIndex(" + arg + ") > toIndex(" + arg0 + ")");
        }
    }

    public void forEach(Consumer<? super E> arg0) {
        Objects.requireNonNull(arg0);
        int arg1 = this.modCount;
        Object[] arg2 = (Object[]) this.elementData;
        int arg3 = this.size;

        for (int arg4 = 0; this.modCount == arg1 && arg4 < arg3; ++arg4) {
            arg0.accept(arg2[arg4]);
        }

        if (this.modCount != arg1) {
            throw new ConcurrentModificationException();
        }
    }

    public Spliterator<E> spliterator() {
        return new ArrayListSpliterator(this, 0, -1, 0);
    }

    public boolean removeIf(Predicate<? super E> arg0) {
        Objects.requireNonNull(arg0);
        int arg1 = 0;
        BitSet arg2 = new BitSet(this.size);
        int arg3 = this.modCount;
        int arg4 = this.size;

        for (int arg5 = 0; this.modCount == arg3 && arg5 < arg4; ++arg5) {
            Object arg6 = this.elementData[arg5];
            if (arg0.test(arg6)) {
                arg2.set(arg5);
                ++arg1;
            }
        }

        if (this.modCount != arg3) {
            throw new ConcurrentModificationException();
        } else {
            boolean arg9 = arg1 > 0;
            if (arg9) {
                int arg10 = arg4 - arg1;
                int arg7 = 0;

                for (int arg8 = 0; arg7 < arg4 && arg8 < arg10; ++arg8) {
                    arg7 = arg2.nextClearBit(arg7);
                    this.elementData[arg8] = this.elementData[arg7];
                    ++arg7;
                }

                for (arg7 = arg10; arg7 < arg4; ++arg7) {
                    this.elementData[arg7] = null;
                }

                this.size = arg10;
                if (this.modCount != arg3) {
                    throw new ConcurrentModificationException();
                }

                ++this.modCount;
            }

            return arg9;
        }
    }

    public void replaceAll(UnaryOperator<E> arg0) {
        Objects.requireNonNull(arg0);
        int arg1 = this.modCount;
        int arg2 = this.size;

        for (int arg3 = 0; this.modCount == arg1 && arg3 < arg2; ++arg3) {
            this.elementData[arg3] = arg0.apply(this.elementData[arg3]);
        }

        if (this.modCount != arg1) {
            throw new ConcurrentModificationException();
        } else {
            ++this.modCount;
        }
    }
//排序
    public void sort(Comparator<? super E> arg0) {
        int arg1 = this.modCount;
        Arrays.sort((Object[]) this.elementData, 0, this.size, arg0);
        if (this.modCount != arg1) {
            throw new ConcurrentModificationException();
        } else {
            ++this.modCount;
        }
    }

}

为自己加油!!!!!!!

原创粉丝点击