美文网首页
关于ArrayList

关于ArrayList

作者: 瓢鳍小虾虎 | 来源:发表于2021-08-02 12:38 被阅读0次

ArrayList简介

  1. ArrayList内部是以动态数组存放数据的,所谓动态数组,不是数组本身可以改变长度,而是保留原有数组引用的情况下创建一个新的数组,使用体验就像是可自动扩容的数组。
  2. ArrayList内部是数组,支持数组的所有特性,通过索引支持随机访问,所以访问效率高,但是插入和删除效率低下。
  3. ArrayList实现了AbstractList抽象类、List接口、所以其更具有了AbstractList和List的功能,AbstractList内部已经实现了获取Iterator和ListIterator的方法,所以ArrayList只需关心对数组操作的方法即List接口的实现。
  4. ArrayList实现了RandomAccess接口、此接口只有声明、没有方法体、表示ArrayList支持随机访问。
  5. ArrayList实现了Cloneable接口、此接口只有声明、没有方法体、表示ArrayList支持克隆。
  6. ArrayList实现了Serializable接口、此接口只有声明、没有方法体、表示ArrayList支持序列化、即可以将ArrayList以流的形式通过ObjectInputStream/ObjectOutputStream来写/读。

ArrayList的扩容

  1. 初始容量为10:使用无参构造的创建ArrayList的时候默认容量为10。
  2. 扩容规则:每次add元素(单个或者一组)的时候,都要先检查容量是否够用。如果发现容量不够,就设置新容量为原有容量1.5倍+1,如果新容量还不够用,就直接把新容量设置为能盛放当前元素量的值。然后就是使用Arrays.copyOf()方法把原数据copy到新数组中去。由此可见,使用ArrayList尽量明确使用上限,自动扩容虽好,但是效率不高。
  3. 为什么是1.5倍:跟源代码中的算法有关“oldCapacity + (oldCapacity >> 1);”
  4. Arrays.copyOf():最终使用的是操作系统的api进行数组复制,效率比我们手写代码要高。
  5. 扩容限制:扩容并非是无限制的,有内存限制,虚拟机限制。

手写ArrayList帮助理解

public class MyArrayList<T> implements Iterable<T>  {
    private T[] theItems;
    private int theSize;
    private static final int DEAULT_CAPACITY=10;

    public MyArrayList(){
        theSize=0;
        ensureCapacity(DEAULT_CAPACITY);

    }

    public void add(T data){
        if(size()==theItems.length){
            ensureCapacity(size()*2+1);
        }
        theItems[size()]=data;
        theSize++;
    }

    public void add(int index,T data){
        if(size()==theItems.length){
            ensureCapacity(size()*2+1);
        }
        for(int i=theSize;i>index;i--){
            theItems[i]=theItems[i-1];
        }
        theItems[index]=data;
        theSize++;
    }

    public T get(int index){
        if(index<0|index>=size()){
            throw new IndexOutOfBoundsException("index error");
        }
        return theItems[index];
    }

    public T remove(int index){
        T removeData=get(index);
        for(int i=index;i<size()-1;i++){
            theItems[i]=theItems[i+1];
        }
        theSize--;
        return removeData;
    }

    public int size(){
        return theSize;
    }

    private void ensureCapacity(int newCapacity){
        if(theSize>newCapacity){
            return;
        }

        T[] old=theItems;
        theItems= (T[]) new Object[newCapacity];
        for(int i=0;i<size();i++){
            theItems[i]=old[i];
        }
    }



    @Override
    public Iterator<T> iterator() {
        return null;
    }

    @Override
    public void forEach(Consumer<? super T> action) {

    }

    @Override
    public Spliterator<T> spliterator() {
        return null;
    }
}

参考文章:
Java容器之ArrayList

相关文章

网友评论

      本文标题:关于ArrayList

      本文链接:https://www.haomeiwen.com/subject/vdgdvltx.html