在集合API中,最初设计的Vector和Hashtable是多线程安全的。例如:对于Vector来说,用来添加和删除元素的方法是同步的。如果只有一个线程与Vector的实例交互,那么,要求获取和释放对象锁便是一种浪费,另外在不必要的时候如果滥用同步化,也有可能会带来死锁。因此,对于更改集合内容的方法,没有一个是同步化的。集合本质上是非多线程安全的,当多个线程与集合交互时,为了使它多线程安全,必须采取额外的措施。

在Collections类 中有多个静态方法,它们可以获取通过同步方法封装非同步集合而得到的集合:

public static Collection synchronizedCollention(Collection c)

public static List synchronizedList(list l)

public static Map synchronizedMap(Map m)

public static Set synchronizedSet(Set s)

public static SortedMap synchronizedSortedMap(SortedMap sm)

public static SortedSet synchronizedSortedSet(SortedSet ss)

这些方法基本上返回具有同步集合方法版本的新类。比如,为了创建多线程安全且由ArrayList支持的List,可以使用如下代码:

List list = Collection.synchronizedList(new ArrayList());

注意,ArrayList实例马上封装起来,不存在对未同步化ArrayList的直接引用(即直接封装匿名实例)。这是一种最安全的途径。如果另一个线程要直接引用ArrayList实例,它可以执行非同步修改。

下面给出一段多线程中安全遍历集合元素的示例。我们使用Iterator逐个扫描List中的元素,在多线程环境中,当遍历当前集合中的元素时,一般希望阻止其他线程添加或删除元素。安全遍历的实现方法如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
import java.util.*;
public class SafeCollectionIteration extends Object {
    public static void main(String[] args) {
        //为了安全起见,仅使用同步列表的一个引用,这样可以确保控制了所有访问
        //集合必须同步化,这里是一个List
        List wordList = Collections.synchronizedList(new ArrayList());
        //wordList中的add方法是同步方法,会获取wordList实例的对象锁
        wordList.add("Iterators");
        wordList.add("require");
        wordList.add("special");
        wordList.add("handling");
        //获取wordList实例的对象锁,
        //迭代时,阻塞其他线程调用add或remove等方法修改元素
        synchronized ( wordList ) {
            Iterator iter = wordList.iterator();
            while ( iter.hasNext() ) {
                String s = (String) iter.next();
                System.out.println("found string: " + s + ", length=" + s.length());
            }
        }
    }
}

这里需要注意的是:在Java语言中,大部分的线程安全类都是相对线程安全的,它能保证对这个对象单独的操作时线程安全的,我们在调用的时候不需要额外的保障措施,但是对于一些特定的连续调用,就可能需要在调用端使用额外的同步手段来保证调用的正确性。例如Vector、HashTable、Collections的synchronizedXxxx()方法包装的集合等。

from: http://www.importnew.com/20624.html

原文出处: 兰亭风雨

Java并发编程(8):多线程环境中安全使用集合API(含代码)相关推荐

  1. 【Java并发编程】之八:多线程环境中安全使用集合API

    在集合API中,最初设计的Vector和Hashtable是多线程安全的.例如:对于Vector来说,用来添加和删除元素的方法是同步的.如果只有一个线程与Vector的实例交互,那么,要求获取和释放对 ...

  2. JAVA并发七(多线程环境中安全使用集合API)

    在集合API中,最初设计的Vector和Hashtable是多线程安全的.例如:对于Vector来说,用来添加和删除元素的方法是同步的.如果只有一个线程与Vector的实例交互,那么,要求获取和释放对 ...

  3. 多线程环境中安全使用集合API(含代码)

    转自: http://blog.csdn.net/ns_code/article/details/17200509 在集合API中,最初设计的Vector和Hashtable是多线程安全的.例如:对于 ...

  4. Java并发编程进阶——多线程的安全与同步

    多线程的安全与同步 多线程的操作原则 多线程 AVO 原则 A:即 Atomic,原子性操作原则.对基本数据类型变量的读和写是保证原子性的,要么都成功,要么都失败,这些操作不可中断. V:即 vola ...

  5. 【Java 并发编程】多线程、线程同步、死锁、线程间通信(生产者消费者模型)、可重入锁、线程池

    并发编程(Concurrent Programming) 进程(Process).线程(Thread).线程的串行 多线程 多线程的原理 多线程的优缺点 Java并发编程 默认线程 开启新线程 `Ru ...

  6. Java 并发编程(多线程)

    线程和进程相关概念 创建线程的方式 线程的生命周期 线程之间如何通讯 线程调度策略 线程安全解决方案 synchronized和Lock的区别 死锁和解决方案 线程常用的方法 wait()和 slee ...

  7. 【Java并发编程 线程安全】21.线程安全集合

    多线程环境使用ArrayList 1.Vector(已过时) 在Java早期使用Vector,在remove.get.set.add.size都是通过synchronized修饰,但是Vector已经 ...

  8. Java并发编程之线程池中的Future

    线程池中的Future: 线程池的典型使用场景 ExecutorService executorService = Executors.newFixedThreadPool(10);//此处Task为 ...

  9. 【Java并发编程】并发编程大合集

    转载请注明出处:http://blog.csdn.net/ns_code/article/details/17539599 为了方便各位网友学习以及方便自己复习之用,将Java并发编程系列内容系列内容 ...

最新文章

  1. 发觉好像视力户籍变差么。。
  2. 【翻译】WF从入门到精通(第十一章):并行活动
  3. 【杂谈】野生在左 科班在右——数据结构学习誓师贴
  4. Linux Graphic DRI Wayland 显示子系统
  5. javascript V8引擎垃圾收集机制
  6. 业内人士惊暴网络求职黑幕!
  7. ubantu的下载和在虚拟机VM中的安装
  8. 如何在Linux操作系统定时重启Tomcat服务?
  9. JSP断点续传多线程链接下载
  10. 操作系统实验及代码(全)
  11. 网络爬虫(一)——爬虫及其实现
  12. JavaIO操作——字节输出流【OutputStream】
  13. c语言课程设计作业心得体会,【c语言课程设计心得体会】 c语言课程设计报告总结...
  14. 渔业古谚语 好吃排“第五”——清蒸白姑鱼
  15. Java爆笑梗,jvav是什么鬼!盘点那些迷你小学生中那些笑死人的梗
  16. NAT 技术最全详解 : 换个马甲就能上网
  17. 多层卷积后感受野的计算
  18. 目标检测 AP计算 (回顾)
  19. 微信小程序二维码如何生成?
  20. JS控制网页中Flash影片的播放(附带各参数)

热门文章

  1. 火了,挡不住了:Facebook Move编程语言入门
  2. FinTech-Blockchain区块链
  3. 从微信AI首席顾问到金融文档智能,一位中科院计算机科学家AI产品化实践
  4. 中国移动互联网趋势报告:教育、金融类App留存率更高
  5. 信贷类行业对于业务管理系统搭建如何下手
  6. 学习笔记(九)——JSON 和 AJAX
  7. android按钮最底,Android:点击按钮后布局上的动画,最低SDK版本为14
  8. python 左旋转字符串
  9. Java实现反向输出链表
  10. 机器学习:如何用相关性实现特征选择?