概要

JDK中提供ArrayList集合方便我们对集合内元素进行增删改查,但是ArrayList为了能够在单线程中快速进行操作其设计并不支持多线程进行操作。ArrayList在多线程环境下可能会产生java.util.ConcurrentModificationException异常。而对于我们需要在多线程下操作集合Jdk为我们内置了支持多线程操作的并发集合类供我们使用。

Vector

Vector始于JDK1.0版本而ArrayList始于JDK1.2版本。Vector对于每个对集合操作的方法都有synchronized进行修饰,即Vector使用同步方法来实现。并且Vector的扩容量与ArrayList有所区别,ArrayList的默认扩容量为0.5倍,而Vector的默认扩容量则为1倍。

synchronizedCollection

对于Vector使用同步方法来实现锁机制而synchronizedCollection则是使用同步代码块来实现锁机制,但是,因为SynchronizedList只是使用同步代码块包裹了ArrayList的方法,而ArrayList和Vector中同名方法的方法体内容并无太大差异,所以在锁定范围和锁的作用域上两者并无却别。而在锁定的对象区别上,SynchronizedList的同步代码块锁定的是mutex对象,Vector锁定的是this对象。那么mutex对象又是什么呢? 其实SynchronizedList有一个构造函数可以传入一个Object,如果在调用的时候显示的传入一个对象,那么锁定的就是用户传入的对象。如果没有指定,那么锁定的也是this对象。也就是说synchronizedCollection可以自定义锁对象,而Vector锁的对象只能是this也就是本身。

CopyOnWriteArrayList

这个并发集合采用的写时复制,读写分离的思想来避免并发时产生的异常。

private E get(Object[] var1, int var2) {
return var1[var2];
}
public E get(int var1) {
return this.get(this.getArray(), var1);
}
public boolean add(E var1) {
ReentrantLock var2 = this.lock;
var2.lock();
boolean var6;
try {
Object[] var3 = this.getArray();
int var4 = var3.length;
Object[] var5 = Arrays.copyOf(var3, var4 + 1);
var5[var4] = var1;
this.setArray(var5);
var6 = true;
} finally {
var2.unlock();
}
return var6;
}

根据以上的源码我们可知,在进行写操作的时候将会事先加锁防止并发问题,然后对原集合进行拷贝一份并且在这份新拷贝的集合中进行数据处理。当数据处理完毕后才将旧集合替换为新集合。而对于读操作在写操作未完成时永远都是以未加锁的形式读取旧的集合。CopyOnWrite容器即写时复制的容器。通俗的理解是当我们往一个容器添加元素的时候,不直接往当前容器添加,而是先将当前容器进行Copy,复制出一个新的容器,然后新的容器里添加元素,添加完元素之后,再将原容器的引用指向新的容器。这样做的好处是我们可以对CopyOnWrite容器进行并发的读,而不需要加锁,因为当前容器不会添加任何元素。所以CopyOnWrite容器也是一种读写分离的思想,读和写不同的容器。

优点:

  1. CopyOnWriteArrayList适合使用在读操作远远大于写操作的场景里,比如缓存。保证读的高性能,适用于以读为主的情况。使用了独占锁,支持多线程下的并发写。

    缺点:
  2. 内存占用问题。在集合进行add操作时内存里会同时驻扎两个对象的内存,旧的对象和新写入的对象。当CopyOnWriteArrayList处于占用内存较大时容易造成频繁GC问题。
  3. 数据一致性问题。CopyOnWrite容器只能保证数据的最终一致性,不能保证数据的实时一致性。所以如果你希望写入的的数据,马上能读到,请不要使用CopyOnWrite容器。【当执行add或remove操作没完成时,get获取的仍然是旧数组的元素】

java - 并发集合 Vector、synchronizedCollection、CopyOnWriteArrayList之间的区别。的更多相关文章

  1. Java并发集合(一)-CopyOnWriteArrayList分析与使用

    CopyOnWriteArrayList分析与使用 原文链接: http://ifeve.com/java-copy-on-write/ 一.Copy-On-Write Copy-On-Write简称 ...

  2. Java并发集合的实现原理

    本文简要介绍Java并发编程方面常用的类和集合,并介绍下其实现原理. AtomicInteger 可以用原子方式更新int值.类 AtomicBoolean.AtomicInteger.AtomicL ...

  3. Java 并发集合的实现原理

    http://www.codeceo.com/article/the-implementation-principle-of-java-concurrent-collection.html 阿凡卢   ...

  4. java并发集合知识点(二)

    我们平时写程序需要经常用到集合类,比如ArrayList.HashMap等,但是这些集合不能够实现并发运行机制,这样在服务器上运行时就会非常的消耗资源和浪费时间,并且对这些集合进行迭代的过程中不能进行 ...

  5. 转:Java并发集合

    引自:http://ifeve.com/concurrent-collections-1/ 并发集合(一)引言 声明:本文是< Java 7 Concurrency Cookbook>的第 ...

  6. Java并发指南14:Java并发容器ConcurrentSkipListMap与CopyOnWriteArrayList

    原文出处http://cmsblogs.com/ 『chenssy』 到目前为止,我们在Java世界里看到了两种实现key-value的数据结构:Hash.TreeMap,这两种数据结构各自都有着优缺 ...

  7. java 常用集合list与Set、Map区别及适用场景总结

     转载请备注出自于:http://blog.csdn.net/qq_22118507/article/details/51576319                  list与Set.Map区别及 ...

  8. java execute、executeQuery和executeUpdate之间的区别

    在用纯JSP做一个页面报警功能的时候习惯性的用executeQuery来执行SQL语句,结果执行update时就遇到问题,语句能执行,但返回结果出现问题,另外还忽略了executeUpdate的返回值 ...

  9. Java自学-集合框架 HashMap和Hashtable的区别

    HashMap和Hashtable之间的区别 步骤 1 : HashMap和Hashtable的区别 HashMap和Hashtable都实现了Map接口,都是键值对保存数据的方式 区别1: Hash ...

随机推荐

  1. JS用map做接口数据映射

    · 接口做数据映射的好处:前端页面自定义的字段不需要和后端字段相同,后端修改字段前端不受影响. · 从接口得到数据 res: let r = res.map(item => { return { ...

  2. generator 和 co模块

    // 类数组的生成器 // 类数组的生成器 function fns() { let obj = {0:1,1:2,2:3,length: 3}, [Symbol.iterator]: functio ...

  3. jSon和Ajax登录功能,ajax数据交互案例

    ajax实例,检测用户与注册 检测用户名是否被占用: 在用户填写完用户名之后,ajax会异步向服务器发送请求,判断用户名是否存在 首先写好静态页面: index.html <!DOCTYPE h ...

  4. Android EditText不可编辑单行显示能滑动查看内容

    遇到问题 有时为了节约界面控件,可以界面的美观,我们会使用单行显示 singleLine,如果使用 Enable = false 输入框文字呈现灰色,并且也无法操作. 想要实现的效果是,单行显示,不能 ...

  5. MFC/QT 学习笔记(四)——MFC基于对话框学习控件(上)

    新建项目->MFC模板->MFC应用程序->应用程序类型:基于对话框->...OK 解决方案资源管理器->资源文件->xxx.rc->进入:资源视图-> ...

  6. ARC-082F Sandglass

    题意 有一个含有两个玻璃球的沙漏,分别称这两个玻璃球为\(

  7. for循环嵌套练习题or99乘法表

    //输出1-10之间的和 public static void whileTest(){ //定义变量用于存储不断变化的和 int sum = 0; //定义变量,用于记录不断变化的被加数 int x ...

  8. ts中类的方法和抽象类

    // 类里面的修饰符 typescript提供三种修饰符 /* public: 公有 在类里面.类外面.子类都可以访问 (默认不加就是public) protected: 保护 在类里面和子类可以访问 ...

  9. 【python基础语法】第6天作业练习题

    ''' 二.作业(每一道题封装成一个函数) 1.输出99乘法表,结果如下:(提示嵌套for循环,格式化输出) 2.有1 2 3 4 这四个数字,设计程序计算能组成多少个互不相同且无重复数字的3位数?分 ...

  10. redis学习三连奏,绝对让你彻底吃透分布式架构精髓

    2020年初,远程办公与直播授课成为国民刚需,腾讯因此免费开放可支持300人同时在线会议的“腾讯会议”.一时之间,这款软件的用户呈爆发性增长,据统计,腾讯会议一天就有近较100倍日常的会议数量. 谈及 ...