对于JDK中的线程安全集合类,个人用的一般是map和队列相关的用的比较多,线程安全的List很少会接触到。开发的时候突然遇到别人问我说有没有线程安全的List…一脸懵逼,所以决定网上找找看有没有相关的结构,别说,还真找到了:
Collections.synchronizedList与CopyOnWriteArrayList
本人之前写的话都是用一个锁来锁定的,今天就来看下这两种结构是不是会比自己用锁会更好。
调试代码如下:
public static void main(String[] args) { List<String> l1 = new CopyOnWriteArrayList<>(); l1.add("1"); List<String> l2 = new ArrayList<>(); List<String> l3 = Collections.synchronizedList(l2); l3.add("a"); }
先看Collections.synchronizedList:
其实就是内部给你synchronize加了个锁…没啥好看的,不过感觉可以简化下你的代码,至少这个里面的方法全部都是加了锁的。
而且锁的是一个变量,所以锁的粒度小。
再看CopyOnWriteArrayList:
当数组有变化时重新建立一个新的数组
一看这个add()就觉得在性能方面肯定不太靠谱:
第一个原因是使用的是Lock,之前分析ReentrantLock的时候说过,虽然它比synchronize提供了更丰富的功能,但是由于它是API级别的,JVM不会对这个锁进行优化,而synchronize之前分析过,它的锁是一步步升级上来的。
第二个原因是它每增加一个元素都要copy一遍旧数组中的元素,生成一个新数组。
好了…接下来的我就不用看了,我觉得一般情况下,前面那个用的会比较多,后面这个的场景我暂时没碰到。