美文网首页
Vector 源码分析

Vector 源码分析

作者: 零星瓢虫 | 来源:发表于2020-12-24 23:02 被阅读0次

Vector 简介

Vector 和 ArrayList 类似,顶级父类为 Collection,区别于 ArrayList 的重要一点,Vector 集合类为线程安全类,而本篇文章也将深入去解析为什么 Vector 可以做到线程安全。

vector 结构图

vector.png

Vector 源码解析

因为和 ArrayList 使用类似,这里直接对 Vector 源码的相关增删改查操作进行分析;

ArrayList 相关源码分析
https://www.jianshu.com/p/0d1815792651

Vector 的构造方法

public Vector(int initialCapacity) {
    this(initialCapacity, 0);
}


public Vector() {
    this(10);
}


public Vector(int initialCapacity, int capacityIncrement) {
    super();
    if (initialCapacity < 0)
        throw new IllegalArgumentException("Illegal Capacity: "+
                                           initialCapacity);
    this.elementData = new Object[initialCapacity];
    this.capacityIncrement = capacityIncrement;
}

Vector 的构造方法初始化容量为 10 的数组,同时初始化变量 capacityIncrement 为 0;

Vector 的 add 方法

public synchronized boolean add(E e) {
    modCount++;
    ensureCapacityHelper(elementCount + 1);// 扩容
    elementData[elementCount++] = e;
    return true;
}

private void ensureCapacityHelper(int minCapacity) {
    // overflow-conscious code
    if (minCapacity - elementData.length > 0)
        grow(minCapacity);
}

针对 add 方法 synchronized 加锁机制,当多线程进行访问的时候先要获取锁才能操作;ensureCapacityHelper 进行判断是否扩容,elementCount 为当前存入的数据数量,当下一位将要大于数组容量的时候就要扩容处理。和 ArrayList 不同的是,这里进行 2n 倍扩容;

Vector 的 remove 方法

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;
}

synchronized 加锁保证同步性,删除之后数组后面位数进行前移动,原数组最后一位置空;同时可以看到每次增删操作都会对 modCount 自增处理;

Vector 的 get 和 set 方法

public synchronized E get(int index) {
    if (index >= elementCount)
        throw new ArrayIndexOutOfBoundsException(index);

    return elementData(index);
}



public synchronized E set(int index, E element) {
    if (index >= elementCount)
        throw new ArrayIndexOutOfBoundsException(index);

    E oldValue = elementData(index);
    elementData[index] = element;
    return oldValue;
}

synchronized 保证同步性;

看完 Vector 的增删改查操作方法可以看到 Vector 主要通过 synchronized 加锁机制保证了数据的同步;

Vector的数据遍历

public synchronized Iterator<E> iterator() {
    return new Itr();
}

private class Itr implements Iterator<E> {
    int cursor;       // index of next element to return
    int lastRet = -1; // index of last element returned; -1 if no such
    int expectedModCount = modCount;

    public boolean hasNext() {
        // Racy but within spec, since modifications are checked
        // within or after synchronization in next/previous
        return cursor != elementCount;
    }

    public E next() {
        synchronized (Vector.this) {
            checkForComodification();
            int i = cursor;
            if (i >= elementCount)
                throw new NoSuchElementException();
            cursor = i + 1;
            return elementData(lastRet = i);
        }
    }

    public void remove() {
        if (lastRet == -1)
            throw new IllegalStateException();
        synchronized (Vector.this) {
            checkForComodification();
            Vector.this.remove(lastRet);
            expectedModCount = modCount;
        }
        cursor = lastRet;
        lastRet = -1;
    }

    final void checkForComodification() {
        if (modCount != expectedModCount)
            throw new ConcurrentModificationException();
    }
}

对比 ArrayList 中的 Itertor 迭代器:

 private class Itr implements Iterator<E> {
    int cursor;       // index of next element to return
    int lastRet = -1; // index of last element returned; -1 if no such
    int expectedModCount = modCount;

    public boolean hasNext() {
        return cursor != size;
    }

    @SuppressWarnings("unchecked")
    public E next() {
        checkForComodification();
        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];
    }

    public void remove() {
        if (lastRet < 0)
            throw new IllegalStateException();
        checkForComodification();

        try {
            ArrayList.this.remove(lastRet);
            cursor = lastRet;
            lastRet = -1;
            expectedModCount = modCount;
        } catch (IndexOutOfBoundsException ex) {
            throw new ConcurrentModificationException();
        }
    }

    final void checkForComodification() {
        if (modCount != expectedModCount)
            throw new ConcurrentModificationException();
    }
}

同样是通过 synchronized 加锁的方式实现数据的同步;

至此,可以得出结论,Vector 主要是在 ArrayList 的基础之上针对数据的操作进行加锁保护,从而实现数据的同步性;

相关文章

  • 搞懂 Java HashMap 源码

    HashMap 源码分析 前几篇分析了 ArrayList , LinkedList ,Vector ,Stack...

  • system.arraycopy native源码解析

    之前在分析ArrayList和Vector源码的时候,发现Sun JDK版本中的ArrayList和Vector大...

  • Vector源码分析

    以下内容整理自互联网,仅用于个人学习 Vector简介 Vector是基于数组实现的,是一个动态数组,其容量能自动...

  • Vector源码分析

    Vector源码分析 jdk7和jdk8不变 与Arraylist扩容方式不同 原始长度为10,代码如下 扩容为2...

  • Vector 源码分析

    Vector 简介 Vector 和 ArrayList 类似,顶级父类为 Collection,区别于 Arra...

  • Vector源码分析

    在上图中可以看到, 和 在继承关系中是平辈关系,可以简单的理解 就是线程安全的 。本文将从源码角度分析 ,如需了解...

  • Vector源码分析

    问题提出 Vector底层采用什么数据结构? Vector 和 ArrayList 有什么区别?什么情况下适用ve...

  • 源码阅读之Vector

    源码阅读是基于JDK7,本篇主要涉及Vector常用方法源码分析。 1.概述Vector实现了一个增长型的Obje...

  • c++学习记录7(GeekBand)

    这周的课程将容器讲完了。自己来总结下容器的东西。 参考:STL源码分析 (一)vector容器 vector的数据...

  • ArrayList/Vector源码分析

    摘要:本篇文章为了巩固自身对于JDK源码的学习里面 ArrayList 在ArrayList源码中,最重要的有2个...

网友评论

      本文标题:Vector 源码分析

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