JDK1.8源码阅读--Vector

Vector继承AbstractList抽象类,实现List, RandomAccess, Cloneable, java.io.Serializable接口。

  • List接口:制定了List的操作规范
  • RandomAccess接口:RandomAccess接口的作用测试
  • Cloneable接口:可以克隆对象(浅拷贝)
  • Serializable接口: 对象序列化

如此看来,Vector与ArrayList的功能结构并无差别,但不同的是Vector是线程安全的。

1. Vector的属性

    /**
     * 保存vector中元素的数组。vector的容量是数组的长度,数组的长度最小值为vector的元素个数。
     * 任何在vector最后一个元素之后的数组元素是null。
     * @serial
     */
    protected Object[] elementData;

    /**
     * vector中实际的元素个数。
     * @serial
     */
    protected int elementCount;

    /**
     * vector需要自动扩容时增加的容量
     * 当vector的实际容量elementCount将要大于它的最大容量时,vector自动增加的容量。
     * 如果capacityIncrement小于或等于0,vector的容量需要增长时将会成倍增长。
     * @serial
     */
    protected int capacityIncrement;

    /** 序列版本号 */
    private static final long serialVersionUID = -2767605614048989439L;

2.Vector的构造函数

1. 构造一个指定容量为capacity、自增容量为capacityIncrement的空vector。

    /**
     * 构造一个指定容量为initialCapacity、自增容量为capacityIncrement的空vector。
     * @param   initialCapacity     初始化容量
     * @param   capacityIncrement   自增容量
     * @throws IllegalArgumentException 如果initialCapacity是负数
     */
    public Vector(int initialCapacity, int capacityIncrement) {
        super();
        if (initialCapacity < 0)
            throw new IllegalArgumentException("Illegal Capacity: "+
                                               initialCapacity);
        this.elementData = new Object[initialCapacity];
        this.capacityIncrement = capacityIncrement;
    }

2. 构造一个指定容量为initialCapacity、自增容量为0的空vector。

    /**
     * 构造一个指定容量为initialCapacity、自增容量为0的空vector。
     * @param   initialCapacity   初始化容量
     * @throws IllegalArgumentException 如果initialCapacity是负数
     */
    public Vector(int initialCapacity) {
        this(initialCapacity, 0);
    }

3. 构造一个指定容量为10、自增容量为0的空vector。

/**

    /**
     * 构造一个指定容量为10、自增容量为0的空vector。
     */
    public Vector() {
        this(10);
    }

4. 使用指定的Collection构造vector。

    /**
     * 构造一个包含特定Collection中所有元素的vector。
     *
     * @param c 用来构造vector的Collection
     * @throws NullPointerException 用来构造vector的Collection是null
     * @since   1.2
     */
    public Vector(Collection c) {
        elementData = c.toArray();
        elementCount = elementData.length;
        // c.toArray might (incorrectly) not return Object[] (see 6260652)
        if (elementData.getClass() != Object[].class)
            elementData = Arrays.copyOf(elementData, elementCount, Object[].class);
    }

3. 重要方法

  • copyInto
    /**
     * 将vector中的所有元素拷贝到指定的数组anArray中
     *
     * @throws NullPointerException 如果指定的数组anArray为null
     * @throws IndexOutOfBoundsException 如果指定的数组anArray的容量小于vector的元素个数
     * @throws ArrayStoreException 如果vector不能被拷贝到anArray中
     * @see #toArray(Object[])
     */
    public synchronized void copyInto(Object[] anArray) {
        System.arraycopy(elementData, 0, anArray, 0, elementCount);
    }
  • trimToSize
    /**
     * 将底层数组的容量调整为当前vector实际元素的个数,来释放空间。
     */
    public synchronized void trimToSize() {
        modCount++;
        // 当实际大小小于底层数组的长度
        int oldCapacity = elementData.length;
        if (elementCount < oldCapacity) {
            // 将底层数组的长度调整为实际大小
            elementData = Arrays.copyOf(elementData, elementCount);
        }
    }
  • ensureCapacity
    /**
     * 增加vector容量
     * 如果vector当前容量小于至少需要的容量,它的容量将增加。
     * 新的容量将在旧的容量的基础上加上capacityIncrement,除非capacityIncrement小于等于0,在这种情况下,容量将会增加一倍。
     * 增加后,如果新的容量还是小于至少需要的容量,那就将容量扩容至至少需要的容量。
     *
     * @param minCapacity 至少需要的容量
     */
    public synchronized void ensureCapacity(int minCapacity) {
        if (minCapacity > 0) {
            modCount++;
            ensureCapacityHelper(minCapacity);
        }
    }
    /**
     * ensureCapacity()方法的unsynchronized实现。
     * ensureCapacity()是同步的,它可以调用本方法来扩容,而不用承受同步带来的消耗
     *
     * @see #ensureCapacity(int)
     */
    private void ensureCapacityHelper(int minCapacity) {
        // 如果至少需要的容量 > 数组缓冲区当前的长度,就进行扩容
        if (minCapacity - elementData.length > 0)
            grow(minCapacity);
    }
    /**
     * 分派给arrays的最大容量
     * 为什么要减去8呢?
     * 因为某些VM会在数组中保留一些头字,尝试分配这个最大存储容量,可能会导致array容量大于VM的limit,最终导致OutOfMemoryError。

     */
    private static final int MAX_ARRAY_SIZE = Integer.MAX_VALUE - 8;
    /**
    * 扩容,保证vector至少能存储minCapacity个元素。
    * 首次扩容时,newCapacity = oldCapacity + ((capacityIncrement > 0)     ?capacityIncrement : oldCapacity);即如果capacityIncrement>0,就加capacityIncrement,如果不是就增加一倍。
    * 如果第一次扩容后,容量还是小于minCapacity,就直接将容量增为minCapacity。
    * 
    * @param minCapacity 至少需要的容量
    */
    private void grow(int minCapacity) {
        // 获取当前数组的容量
        int oldCapacity = elementData.length;
        // 扩容。新的容量=当前容量+当前容量/2.即将当前容量增加一倍
        int newCapacity = oldCapacity + ((capacityIncrement > 0) ?
                                         capacityIncrement : oldCapacity);
        // 如果扩容后的容量还是小于想要的最小容量
        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) {
        // 如果minCapacity<0,抛出异常
        if (minCapacity < 0) // overflow
            throw new OutOfMemoryError();
        // 如果想要的容量大于MAX_ARRAY_SIZE,则分配Integer.MAX_VALUE,否则分配MAX_ARRAY_SIZE
        return (minCapacity > MAX_ARRAY_SIZE) ?
            Integer.MAX_VALUE :
            MAX_ARRAY_SIZE;
    }
  • setSize
    /**
     * 设置vector的容量。
     * 如果newSize大于现有vector的元素的个数,则将vector的大小设置为newSize。如果newSize小于现有vector的元素的个数,则将vector中索引在newSize(包括newSize)之后的元素都置为null。
     * @param  newSize   设置容量后的新大小
     * @throws ArrayIndexOutOfBoundsException 如果newSize为负数negative
     */
    public synchronized void setSize(int newSize) {
        modCount++;
        if (newSize > elementCount) {
            ensureCapacityHelper(newSize);
        } else {
            for (int i = newSize ; i < elementCount ; i++) {
                elementData[i] = null;
            }
        }
        elementCount = newSize;
    }
  • elements
    /**
     * 返回vector中所有元素的Enumeration。
     * Enumeration提供用于遍历vector中所有元素的方法
     * @return  返回vector中所有元素的Enumeration。
     * @see     Iterator
     */
    public Enumeration elements() {
        return new Enumeration() {
            int count = 0;

            public boolean hasMoreElements() {
                return count < elementCount;
            }

            public E nextElement() {
                synchronized (Vector.this) {
                    if (count < elementCount) {
                        return elementData(count++);
                    }
                }
                throw new NoSuchElementException("Vector Enumeration");
            }
        };
    }
  • contains
    /**
     * 查看vector中是否包含元素o
     *
     * @param o 元素o
     * @return {@code true} vector中是否包含元素o
     */
    public boolean contains(Object o) {
        return indexOf(o, 0) >= 0;
    }
  • public int indexOf(Object o)
    /**
     * 正向遍历vector,返回第一次出现元素o的索引
     * 如果vector中不包含元素o,返回-1
     *
     * @param o 需要查找的元素
     * @return 返回第一次出现元素o的索引。如果vector中不包含元素o,返回-1
     */
    public int indexOf(Object o) {
        return indexOf(o, 0);
    }
  • public synchronized int indexOf(Object o, int index)
    /**
     * 从索引为index的位置正向遍历vector,返回第一次出现元素o的索引。
     * 如果vector中不包含元素o,返回-1
     * @param o 想要查找的元素
     * @param index 开始查找位置的索引
     * @return 返回第一次出现元素o的索引。如果vector中不包含元素o,返回-1
     * @throws IndexOutOfBoundsException 如果index为负数
     * @see     Object#equals(Object)
     */
    public synchronized int indexOf(Object o, int index) {
        if (o == null) {
            for (int i = index ; i < elementCount ; i++)
                if (elementData[i]==null)
                    return i;
        } else {
            for (int i = index ; i < elementCount ; i++)
                if (o.equals(elementData[i]))
                    return i;
        }
        return -1;
    }
  • public synchronized int lastIndexOf(Object o)
    /**
     * 逆向遍历vector,返回第一次出现元素o的索引。
     * 如果vector中不包含元素o,返回-1
     *
     * @param o 需要查找的元素
     * @return 返回第一次出现元素o的索引。如果vector中不包含元素o,返回-1
     */
    public synchronized int lastIndexOf(Object o) {
        return lastIndexOf(o, elementCount-1);
    }
  • public synchronized int lastIndexOf(Object o, int index)
    /**
     * 从索引为index的位置逆向遍历vector,返回第一次出现元素o的索引。
     * 如果vector中不包含元素o,返回-1 
     * @param o 想要查找的元素
     * @param index 开始查找位置的索引
     * @return 返回第一次出现元素o的索引。如果vector中不包含元素o,返回-1
     * @throws IndexOutOfBoundsException 如果index大于或等于vector的大小
     */
    public synchronized int lastIndexOf(Object o, int index) {
        if (index >= elementCount)
            throw new IndexOutOfBoundsException(index + " >= "+ elementCount);

        if (o == null) {
            for (int i = index; i >= 0; i--)
                if (elementData[i]==null)
                    return i;
        } else {
            for (int i = index; i >= 0; i--)
                if (o.equals(elementData[i]))
                    return i;
        }
        return -1;
    }
  • elementAt
    /**
     * 返回索引为index的元素。 
     * @param      index   查找的元素的索引
     * @return     索引为index的元素
     * @throws ArrayIndexOutOfBoundsException 索引小于0或大于vector的大小
     */
    public synchronized E elementAt(int index) {
        if (index >= elementCount) {
            throw new ArrayIndexOutOfBoundsException(index + " >= " + elementCount);
        }

        return elementData(index);
    }
  • public synchronized E firstElement()
    /**
     * 返回vector的第一个元素  
     * @return     vector的第一个元素
     * @throws NoSuchElementException 如果vector没有元素components
     */
    public synchronized E firstElement() {
        if (elementCount == 0) {
            throw new NoSuchElementException();
        }
        return elementData(0);
    }
  • public synchronized E lastElement()
    /**
     * 返回vector的最后一个元素  
     * @return vector的最后一个元素
     * @throws NoSuchElementException 如果vector没有元素
     */
    public synchronized E lastElement() {
        if (elementCount == 0) {
            throw new NoSuchElementException();
        }
        return elementData(elementCount - 1);
    }
  • setElementAt(E obj, int index)
    /**
     * 替换索引为index的元素为指定的对象0 
     * 索引必须大于等于0而且小于vector的大小 
     * @param      obj     指定的对象0
     * @param      index   被替换元素的索引
     * @throws ArrayIndexOutOfBoundsException 索引必须小于等于0或者大于vector的大小
     */
    public synchronized void setElementAt(E obj, int index) {
        if (index >= elementCount) {
            throw new ArrayIndexOutOfBoundsException(index + " >= " +
                                                     elementCount);
        }
        elementData[index] = obj;
    }
  • removeElementAt(int index)
    /**
     * 删除在特定索引index的元素。在索引index之后的元素左移,索引减1。 
     * 索引index大小必须大于等于0且小于vector的大小 
     * @param      index   需要删除的元素的索引
     * @throws ArrayIndexOutOfBoundsException 索引index小于0或大于vector的大小
     */
    public synchronized void removeElementAt(int index) {
        modCount++;
        if (index >= elementCount) {
            throw new ArrayIndexOutOfBoundsException(index + " >= " +
                                                     elementCount);
        }
        else if (index < 0) {
            throw new ArrayIndexOutOfBoundsException(index);
        }
        int j = elementCount - index - 1;
        if (j > 0) {
            System.arraycopy(elementData, index + 1, elementData, index, j);
        }
        elementCount--;
        elementData[elementCount] = null; /* to let gc do its work */
    }
  • public synchronized void insertElementAt(E obj, int index)
    /**
     * 在指定索引index处插入指定对象obj。索引大于或等于index的元素右移,索引+1。
     * 索引必须大于等于0而且小于等于vector的大小。
     *
     * @param      obj     指定对象
     * @param      index   指定索引
     * @throws ArrayIndexOutOfBoundsException 索引小于0或者大于vector的大小
     */
    public synchronized void insertElementAt(E obj, int index) {
        modCount++;
        if (index > elementCount) {
            throw new ArrayIndexOutOfBoundsException(index
                                                     + " > " + elementCount);
        }
        ensureCapacityHelper(elementCount + 1);
        System.arraycopy(elementData, index, elementData, index + 1, elementCount - index);
        elementData[index] = obj;
        elementCount++;
    }
  • public synchronized void addElement(E obj)
    /**
     * 在vector的末尾添加指定元素obj,vector大小+1. 如果容量大与现有容量,要扩充容量。
     *
     * @param   obj   the component to be added
     */
    public synchronized void addElement(E obj) {
        modCount++;
        ensureCapacityHelper(elementCount + 1);
        elementData[elementCount++] = obj;
    }
  • public synchronized boolean removeElement(Object obj)
    /**
     * 正向遍历vector,当指定元素obj第一次出现时,删除它,它之后的元素左移一位。
     * @return  a clone of this vector
     */
    public synchronized boolean removeElement(Object obj) {
        modCount++;
        int i = indexOf(obj);
        if (i >= 0) {
            removeElementAt(i);
            return true;
        }
        return false;
    }
  • public synchronized void removeAllElements()
    /**
     * 删除vector中所有元素,并将大小置为0。
     */
    public synchronized void removeAllElements() {
        modCount++;
        // Let gc do its work
        for (int i = 0; i < elementCount; i++)
            elementData[i] = null;

        elementCount = 0;
    }
  • clone()
    /**
     * 返回当前vector的克隆. 该克隆会指向一个全新的vector。
     * @return  a clone of this vector
     */
    public synchronized Object clone() {
        try {
            @SuppressWarnings("unchecked")
                Vector v = (Vector) super.clone();
            v.elementData = Arrays.copyOf(elementData, elementCount);
            v.modCount = 0;
            return v;
        } catch (CloneNotSupportedException e) {
            // this shouldn't happen, since we are Cloneable
            throw new InternalError(e);
        }
    }
  • public synchronized Object[] toArray()
    /**
     * 将vector中所有元素按顺序存放到数组中
     *
     * @since 1.2
     */
    public synchronized Object[] toArray() {
        return Arrays.copyOf(elementData, elementCount);
    }
  • public synchronized T[] toArray(T[] a)
    /**
     * 返回Vector的模板数组。所谓模板数组,即可以将T设为任意的数据类型。 
     * @param a 将要存放vector中所有元素的数组
     * @return 存放vector中所有元素的数组
     * @throws ArrayStoreException 如果vector中元素不能转换为T
     * @throws NullPointerException 如果指定的数组为null
     * @since 1.2
     */
    @SuppressWarnings("unchecked")
    public synchronized  T[] toArray(T[] a) {
        // 如果数组a的大小 < vector的元素个数
        if (a.length < elementCount)
            // 则新建一个T[]数组,数组大小是“Vector的元素个数”,并将“Vector”全部拷贝到新数组中
            return (T[]) Arrays.copyOf(elementData, elementCount, a.getClass());

        //若数组a的大小 >= vector的元素个数,则将Vector的全部元素都拷贝到数组a中。
        System.arraycopy(elementData, 0, a, 0, elementCount);

        if (a.length > elementCount)
            a[elementCount] = null;

        return a;
    }

    // Positional Access Operations
  • E elementData(int index)
    /**
     * 获取索引为index的元素
     */
    @SuppressWarnings("unchecked")
    E elementData(int index) {
        return (E) elementData[index];
    }
  • public synchronized E get(int index)
    /**
     * 返回vector中索引位置为index的元素. 
     * @param index 要返回的元素的索引
     * @return 索引为index的元素
     * @throws ArrayIndexOutOfBoundsException 如果索引小于0或者索引大于等于vector的大小 
     * @since 1.2
     */
    public synchronized E get(int index) {
        if (index >= elementCount)
            throw new ArrayIndexOutOfBoundsException(index);

        return elementData(index);
    }
  • public synchronized E set(int index, E element)
    /**
     * 将索引为index的元素替换为指定元素element,并返回被替换的旧元素。 
     * @param index 被替换的元素的位置
     * @param element 指定元素
     * @return 被替换的旧元素
     * @throws ArrayIndexOutOfBoundsException 如果索引小于0或者索引大于等于vector的大小
     * @since 1.2
     */
    public synchronized E set(int index, E element) {
        if (index >= elementCount)
            throw new ArrayIndexOutOfBoundsException(index);

        E oldValue = elementData(index);
        elementData[index] = element;
        return oldValue;
    }
  • public synchronized boolean add(E e)
    /**
     * 添加指定元素到vector的末尾. 
     * @param e 被添加到vector的元素
     * @return true
     * @since 1.2
     */
    public synchronized boolean add(E e) {
        modCount++;
        ensureCapacityHelper(elementCount + 1);
        elementData[elementCount++] = e;
        return true;
    }
  • **public boolean remove(Object o) **
    /**
     * 正向遍历vector,当指定对象o第一次出现时,删除它,它之后的元素左移一位。 
     * @param o 被删除的元素
     * @return 如果对象在vector中存在,返回true
     * @since 1.2
     */
    public boolean remove(Object o) {
        return removeElement(o);
    }
  • public void add(int index, E element)
    /**
     * 在指定索引index处插入指定对象element。索引大于或等于index的元素右移,索引+1。
     * 索引必须大于等于0而且小于等于vector的大小。 
     * @param index 指定索引
     * @param element 指定对象element
     * @throws ArrayIndexOutOfBoundsException 索引必须小于0或者大于vector的大小
     * @since 1.2
     */
    public void add(int index, E element) {
        insertElementAt(element, index);
    }
  • public synchronized E remove(int index)
    /**
     * 删除在特定索引index的元素。在索引index之后的元素左移,索引减1。 
     * 索引index大小必须大于等于0且小于vector的大小 
     * @param      index   需要删除的元素的索引
     * @throws ArrayIndexOutOfBoundsException 索引index小于0或大于vector的大小
     * @since 1.2
     */
    public synchronized E remove(int index) {
        modCount++;
        if (index >= elementCount)
            throw new ArrayIndexOutOfBoundsException(index);
        E oldValue = elementData(index);

        int numMoved = elementCount - index - 1;
        if (numMoved > 0)
            System.arraycopy(elementData, index+1, elementData, index,
                             numMoved);
        elementData[--elementCount] = null; // Let gc do its work

        return oldValue;
    }

-clear()

    /**
     * 清空vector
     * @since 1.2
     */
    public void clear() {
        removeAllElements();
    } 
  • public synchronized boolean containsAll(Collection c)
    /**
     * 返回vector是否完全包含指定的集合c 
     * @param   c 指定的集合c
     * @return  返回vector是否完全包含指定的集合c
     * @throws NullPointerException 指定的集合c为null
     */
    public synchronized boolean containsAll(Collection c) {
        return super.containsAll(c);
    }
  • public synchronized boolean addAll(Collection c)
    /**
     * 添加指定集合c中的所有元素到vector的末尾 
     * @param c 指定集合c
     * @return 如果指定集合c的长度大于0
     * @throws NullPointerException 如果指定集合c为null
     * @since 1.2
     */
    public synchronized boolean addAll(Collection c) {
        modCount++;
        Object[] a = c.toArray();
        int numNew = a.length;
        ensureCapacityHelper(elementCount + numNew);
        System.arraycopy(a, 0, elementData, elementCount, numNew);
        elementCount += numNew;
        return numNew != 0;
    }
  • public synchronized boolean removeAll(Collection c)
    /**
     * 删除vector中vector和指定集合c中共有的元素。 
     * @param c 指定集合c
     * @return true 如果删除成功
     * @throws ClassCastException 如果vector中有元素和指定集合中的元素类型不匹配
     * @throws NullPointerException 如果vector中含有null,而指定集合不支持null
     * @since 1.2
     */
    public synchronized boolean removeAll(Collection c) {
        return super.removeAll(c);
    }
  • public synchronized boolean retainAll(Collection c)
    /**
     * 从vector中移除未包含在指定集合c中的所有元素
     * @param c 指定集合c
     * @return 
     * @throws ClassCastException 如果vector和指定集合中有元素类型不匹配
     * @throws NullPointerException 如果vector中含有null,而指定集合不支持null
     * @since 1.2
     */
    public synchronized boolean retainAll(Collection c) {
        return super.retainAll(c);
    }
  • public synchronized boolean addAll(int index, Collection c)
    /**
     * 在vector的指定索引index处插入指定集合c。在索引index处的元素和之后的元素右移一位。 
     * @param index 指定索引
     * @param c 指定集合
     * @return 
     * @throws ArrayIndexOutOfBoundsException 索引index小于0或大于vector的大小
     * @throws NullPointerException 指定的集合为null
     * @since 1.2
     */
    public synchronized boolean addAll(int index, Collection c) {
        modCount++;
        if (index < 0 || index > elementCount)
            throw new ArrayIndexOutOfBoundsException(index);

        Object[] a = c.toArray();
        int numNew = a.length;
        ensureCapacityHelper(elementCount + numNew);

        int numMoved = elementCount - index;
        if (numMoved > 0)
            System.arraycopy(elementData, index, elementData, index + numNew,
                             numMoved);

        System.arraycopy(a, 0, elementData, index, numNew);
        elementCount += numNew;
        return numNew != 0;
    }

你可能感兴趣的:(JDK1.8源码阅读--Vector)