Java的容器的线程安全
2013-06-25 21:30
197 查看
http://blog.sina.com.cn/s/blog_5efa3473010129pw.html
线程安全:多个线程操作容器的时候,互相之间不会带来意想不到的影响;
有些容器是线程安全的(Vector,ConcurrentLinkedQueue等),有些则不是(list等),利用类似 private static List<Task> taskQueue = Collections.synchronizedList(new LinkedList<Task>());的方法可以得到本身不是线程安全的容易的线程安全的状态,但是要注意的是线程安全仅仅指的是如果直接使用它提供的函数,比如:queue.add(obj); 或者 queue.poll(obj);,这样我们自己不需要做任何同步。
但如果是非原子操作,比如:
1. if(!queue.isEmpty()) {
2. queue.poll(obj);
3. }
我们很难保证,在调用了isEmpty()之后,poll()之前,这个queue没有被其他线程修改。
所以对于这种情况,我们还是需要自己同步:
1. synchronized(queue) {
2. if(!queue.isEmpty()) {
3. queue.poll(obj);
4. }
5. }
对于Collections.synchronizedList(new LinkedList<Task>()),
在返回的列表上进行迭代时,用户必须手工在返回的列表上进行同步:
不遵从此建议将导致无法确定的行为。
线程安全:多个线程操作容器的时候,互相之间不会带来意想不到的影响;
有些容器是线程安全的(Vector,ConcurrentLinkedQueue等),有些则不是(list等),利用类似 private static List<Task> taskQueue = Collections.synchronizedList(new LinkedList<Task>());的方法可以得到本身不是线程安全的容易的线程安全的状态,但是要注意的是线程安全仅仅指的是如果直接使用它提供的函数,比如:queue.add(obj); 或者 queue.poll(obj);,这样我们自己不需要做任何同步。
但如果是非原子操作,比如:
1. if(!queue.isEmpty()) {
2. queue.poll(obj);
3. }
我们很难保证,在调用了isEmpty()之后,poll()之前,这个queue没有被其他线程修改。
所以对于这种情况,我们还是需要自己同步:
1. synchronized(queue) {
2. if(!queue.isEmpty()) {
3. queue.poll(obj);
4. }
5. }
对于Collections.synchronizedList(new LinkedList<Task>()),
在返回的列表上进行迭代时,用户必须手工在返回的列表上进行同步:
List list = Collections.synchronizedList(new ArrayList()); ... synchronized(list) { Iterator i = list.iterator(); // Must be in synchronized block while (i.hasNext()) foo(i.next()); }
不遵从此建议将导致无法确定的行为。
相关文章推荐
- java线程安全的容器类
- 【转载】Java容器的线程安全
- java线程安全之同步类容器与并发类容器(十二)
- Java容器的线程安全情况
- Java并发:线程安全的容器:同步和并发
- Java线程安全的容器与介绍
- java 线程-生命周期-锁-阻塞-生成消费模式-安全容器
- java线程安全的容器有哪些?
- Java线程(一):线程安全与不安全
- Java并发系列-8、线程安全与共享资源
- Java的多线程编程模型2--怎样才线程安全
- 【java】泛型和类型安全的容器ArrayList
- java线程安全和锁机制详解
- java线程安全问题之静态变量、实例变量、局部变量
- Java赋值的线程安全问题
- Java线程安全的实现方法
- 操作集合的线程安全考虑——java
- Java—java中如何安全的结束一个正在运行的线程
- Java线程安全和非线程安全
- Java多线程总结之线程安全队列Queue