跟着实例学习java多线程7-对象的组合发布
2015-02-03 00:21
501 查看
我们学习线程安全与同步的知识目的就是要实现一些可复用组件或编写出更大的程序。
java中类是对象抽象,那么怎么实现一个线程安全类是我们必须要知道的并正确使用的技术。
在设计线程安全类的过程中,需要包含以下三个基本元素:
找出构成对象状态的所有变量。
找出约束状态变量的不变性条件。
建立对象状态的并发访问管理策略。
方法getId被原子化,这里主要是因为id的状态判断是一个约束条件,而这个约束条件决定了id的值的有效性,所以必须对这步操作做原子化处理。
实例封闭
我们在编写程序中多数会使用一些非线程安全的对象来实现数据的存储,这样的对象如果被多线程访问或是写入,那么就必须做线程安全处理,最好的方式是线程中的封闭处理。让我们来看一个经常会用到的实例:
我们利用LinkedList来实现一个先进先出队列,但是LinkedList不是线程安全的,所以我们把它进行实例封闭,这样任何一个线程都可以访问它的值。
线程安全性委托
我们经常会使用ConcurrentHashMap这样的并发对象,它们是java提供的并发变成对象,它们在内部实现了同步机制,所以它们是线程安全的,我们可以把不安全对象Map的访问完全交给它来委托管理,这样通过final类型的处理,我们只需要通过Collections的浅拷贝实现Map的线程安全。
实例我们先不提供,大家可以回去试着写一下,下一节我们在来讨论。
利用现有线程安全的类实现并发添加功能
java api中有很多这样的类,例如:Vector、HashTable等,让我们来看一个例子。
我们利用Vector来实现了一个监听器列表的操作。
同步类是我们在实践中经常要实现的类,我们要多思考这样的问题,我的类需要写成线程安全的吗?
java中类是对象抽象,那么怎么实现一个线程安全类是我们必须要知道的并正确使用的技术。
在设计线程安全类的过程中,需要包含以下三个基本元素:
找出构成对象状态的所有变量。
找出约束状态变量的不变性条件。
建立对象状态的并发访问管理策略。
package com.home.thread.thread7; import com.home.thread.safe; public class Counter { /** * @author gaoxu * */ public class SafeThread { private int id = 0; @safe public synchronized int getId(){ if(id==Integer.MAX_VALUE) throw new IllegalStateException("counter overflow"); return ++id; } } }
方法getId被原子化,这里主要是因为id的状态判断是一个约束条件,而这个约束条件决定了id的值的有效性,所以必须对这步操作做原子化处理。
实例封闭
我们在编写程序中多数会使用一些非线程安全的对象来实现数据的存储,这样的对象如果被多线程访问或是写入,那么就必须做线程安全处理,最好的方式是线程中的封闭处理。让我们来看一个经常会用到的实例:
package com.uskytec.ubc.foundation.queue; import java.util.LinkedList; import com.uskytec.ubc.foundation.entity.SmsSubmitEntity; /**保存到短信猫的信息的队列 * @author GaoXu * */ public class LNSentCache { private static LNSentCache instance = null; public synchronized static LNSentCache getInstance() { if (instance == null) instance = new LNSentCache(); return instance; } private final static LinkedList<SmsSubmitEntity> routeCache = new LinkedList<SmsSubmitEntity>(); /** * 添加到指定缓冲池 * @param type * @param smgpConfigID * @param submitMsg * @return */ public synchronized int add(SmsSubmitEntity sms) { routeCache.add(sms); return 1; } /** * 得到指定缓冲池的的对象 * @param sgipConfigID * @return */ public synchronized Object get() { if (routeCache != null&&routeCache.size()>0) return routeCache.removeFirst(); return null; } }
我们利用LinkedList来实现一个先进先出队列,但是LinkedList不是线程安全的,所以我们把它进行实例封闭,这样任何一个线程都可以访问它的值。
线程安全性委托
我们经常会使用ConcurrentHashMap这样的并发对象,它们是java提供的并发变成对象,它们在内部实现了同步机制,所以它们是线程安全的,我们可以把不安全对象Map的访问完全交给它来委托管理,这样通过final类型的处理,我们只需要通过Collections的浅拷贝实现Map的线程安全。
实例我们先不提供,大家可以回去试着写一下,下一节我们在来讨论。
利用现有线程安全的类实现并发添加功能
java api中有很多这样的类,例如:Vector、HashTable等,让我们来看一个例子。
package com.gome.qiantai.tools; import java.util.Vector; import com.gome.qiantai.service.IAppraiseWriterObserverService; /** * @author gaoxu * */ public class ObserverCache { private static ObserverCache instance = null; public synchronized static ObserverCache getInstance() { if (instance == null) instance = new ObserverCache(); return instance; } private static Vector<IAppraiseWriterObserverService> obs = new Vector<IAppraiseWriterObserverService>(); public Vector<IAppraiseWriterObserverService> getObs(){ return obs; } }
我们利用Vector来实现了一个监听器列表的操作。
同步类是我们在实践中经常要实现的类,我们要多思考这样的问题,我的类需要写成线程安全的吗?
相关文章推荐
- 跟着实例学习java多线程6-如何正确发布线程安全的对象
- 跟着实例学习java多线程2-synchronized锁住的是对象还是代码
- 【面向对象课程项目:纸牌】Java实例学习(一):优秀源码的分析
- 【python学习笔记】python中的模块,类,函数,对象,实例(与JAVA的比较)
- java 学习实例,实现空对象,和重写了,Comparator 的类实现了对于容器的比较!
- Java代理学习-创建动态类的实例对象及调用其方法
- Java学习第6天:面向对象(2)对象实例
- 【面向对象课程项目:纸牌】Java实例学习(二):优秀源码与自己模型的对比
- Java学习日记之类和对象:静态成员与实例成员
- 跟着实例学习java多线程9-并发容器
- java基础学习05(面向对象基础01--类实例分析)
- mina学习基础-入门实例-传输java对象(二)
- 跟着实例学习java多线程4-内存可见性
- 通过实例学习Java对象的构造过程
- Java学习笔记-------使用DataOutputStream 、DataInputStream 组合实现C/S通信 :实例
- 通过实例学习Java对象的构造过程
- Java并发学习笔记(9)组合对象的安全同步
- 跟着实例学习java多线程3-synchronized的多种写法有何区别?
- 通过实例学习Java对象的构造过程
- Java学习之对象实例化