并发容器ConcurrentHashMap和CopyOnWriteArrayList

ConcurrentHashMap(用于替代HashMap)

    该类并非在每一个方法上加上同步锁,而是使用分段锁。迭代时不会抛出ConcurrentModificationException,因此不须要在迭代的时候,加上同步锁 。不过在获取size和isEmpty的时候,可能只是个估计值,而不是精确值。java

    一个ConcurrentHashMap由多个segment组成,每个segment都包含了一个HashEntry数组的hashtable, 每个segment包含了对本身的hashtable的操做,好比get,put,replace等操做,这些操做发生的时候,对本身的hashtable进行锁定(分段锁)。因为每个segment写操做只锁定本身的hashtable,因此可能存在多个线程同时写的状况,性能无疑好于只有一个hashtable锁定的状况。数组

CopyOnWriteArrayList(用来替代同步List)

    迭代期间不须要加锁。其基本思路是,从一开始你们都在共享同一个内容,当某我的想要修改这个内容的时候,才会真正把内容Copy出去造成一个新的内容而后再改,这是一种延时懒惰策略。并发

   通俗的理解是当咱们往一个容器添加元素的时候,不直接往当前容器添加,而是先将当前容器进行Copy,复制出一个新的容器,而后新的容器里添加元素,添加完元素以后,再将原容器的引用指向新的容器。这样作的好处是咱们能够对CopyOnWrite容器进行并发的读,而不须要加锁,由于当前容器不会添加任何元素。因此CopyOnWrite容器也是一种读写分离的思想,读和写不一样的容器。下面是增长的时候的源码:    性能

public boolean add(E e) {
    final ReentrantLock lock = this.lock;
    lock.lock();
    try {
        Object[] elements = getArray();
        int len = elements.length;
        Object[] newElements = Arrays.copyOf(elements, len + 1);
        newElements[len] = e;
        setArray(newElements);
        return true;
    } finally {
        lock.unlock();
    }
}

    因为添加元素的时候,会拷贝出一个副本再添加,所以这个list只适用于遍历多,修改少的场景。this

相关文章
相关标签/搜索