研磨设计模式学习笔记之单例模式
来源:互联网 发布:澳门十月初五饼家淘宝 编辑:程序博客网 时间:2024/04/30 05:18
1、单例模式定义:保证一个类仅有一个实例,并提供一个访问它的全局访问点 。
2、单例模式结构及说明:Singleton:负责创建Singleton类自己的唯一实例,并提供一个getInstance的方法,让外部来访问这个类的唯一实例。
3、单例模式示例代码:
3.1 单例模式又分为饿汉式与懒汉式单例模式。
饿与懒的区别,饿表示的是在程序加载的时候即创建一个静态实例。懒顾名思义即当在需要他的时候才会创建。
3.2 恶汉式代码:
package singleton;/** * 懒汉式单例模式 * @author Administrator * */public class SingletonSample2 {/** * 定义一个变量来存储创建好的类的实例 */private static SingletonSample2 uniqueInstance= null;/** * 私有构造方法,可以在内部控制创建实例的数目 */private SingletonSample2(){}/** * 定义一个方法来为客户端提供实例 * @return */public static synchronized SingletonSample2 getInstance(){//判断存储实例的变量是否有值if(null == uniqueInstance){//如果没有,就创建一个类实例,并把值赋给存储类实例的变量uniqueInstance = new SingletonSample2();}//有值就直接返回return uniqueInstance;}/** * 定义自己的方法 */public void singletonOperation(){}/** * 定义自己的属性 */private String singletonData;public String getSingletonData() {return singletonData;}public void setSingletonData(String singletonData) {this.singletonData = singletonData;}}测试类
public class SingletonTest {public static void main(String[] args) {SingletonSample2 s21 = SingletonSample2.getInstance();SingletonSample2 s22 = SingletonSample2.getInstance();System.out.println(s21==s22);}}测试结果:返回true
3.2 懒汉式代码:
package singleton;/** * 恶汉式单例模式 * @author Administrator * */public class SingletonSample1 {/** * 定义一个变量来存储创建好的类的实例,直接在这里创建类的实例,只能创建一次 */private static SingletonSample1 uniqueInstance= new SingletonSample1();/** * 私有构造方法,可以在内部控制创建实例的数目 */private SingletonSample1(){}/** * 定义一个方法来为客户端提供实例 * @return */public static SingletonSample1 getInstance(){return uniqueInstance;}/** * 定义自己的方法 */public void singletonOperation(){}/** * 定义自己的属性 */private String singletonData;public String getSingletonData() {return singletonData;}public void setSingletonData(String singletonData) {this.singletonData = singletonData;}}
4、单例模式线程安全性:不加同步的懒汉式是线程不安全的,在多线程的环境中可能会导致并发问题。而饿汉式是线程安全的,因为虚拟机保证只会装载一次,在装载类的时候不会发生并发的。
4.1 如何实现懒汉式线程安全呢? 当然可以直接在getInstance()方法上加上synchronized关键字。但这样就会降低整个访问的速度,而且每次都要判断。故出现了双重检查加锁。
4.2 双重检查加锁机制:指的是并不是每次进入getInstance方法都需要同步,而是先不同步,进入方法过后,先检查实例是否存在,如果不存在才进入下面的同步块,这是第一重检查。进入同步块过后,再次检查实例是否存在如果不存在,就在同步块的情况下创建一个实例,这就是第二重检查。这样一来,就只需要同步一次了。从而减少了多次在同步的情况下进行的判断而浪费的时间。 不多说,上代码。
package singleton;/** * 双重检查加锁懒汉式单例模式 * @author Administrator * */public class SingletonSample3 {/** * 定义一个变量来存储创建好的类的实例需添加volatile修饰 */private volatile static SingletonSample3 uniqueInstance= null;/** * 私有构造方法,可以在内部控制创建实例的数目 */private SingletonSample3(){}/** * 定义一个方法来为客户端提供实例 * @return */public static SingletonSample3 getInstance(){//判断存储实例的变量是否有值if(null == uniqueInstance){//同步块,线程安全地创建实例synchronized (SingletonSample3.class) {//再次检查实例是否存在,如果不存在才真正的创建实例if(null == uniqueInstance){uniqueInstance = new SingletonSample3();}}}//有值就直接返回return uniqueInstance;}/** * 定义自己的方法 */public void singletonOperation(){}/** * 定义自己的属性 */private String singletonData;public String getSingletonData() {return singletonData;}public void setSingletonData(String singletonData) {this.singletonData = singletonData;}}(建议双重检查加锁用在java5及以上版本。)
5、单例模式的更好实现方式:类级内部类。
5.1 类级内部类:有static修饰的成员式内部类。如果没有static修饰的成员内部类被称为对象内部类。
5.2 多线程缺省同步锁。
在多线程开发中,为了解决并发问题,主要是通过使用synchronized来加互斥锁进行同步控制。但是某些情况中,虚拟机已经隐含地为您执行了同步,这些情况就不用直接再来进行同步控制了。这些情况包括:
- 由静态初始化器(在静态字段上或static{}块中的初始化器)初始化数据时
- 访问final字段时
- 在创建线程之间创建对象
- 线程可以看见它要处理的对象时
5.3 更为简单的实现单例模式实例代码
package singleton;/** * 双重检查加锁懒汉式单例模式 * @author Administrator * */public class SingletonSample4 {/** * 类级内部类 * 没有绑定关系,而且只有在调用的时候才会加载,从而实现了延迟加载 */private static class SingletonHolder{/** * 静态初始化器,由JVM来保证线程安全 */private static SingletonSample4 instance = new SingletonSample4();}public static SingletonSample4 getInstance(){return SingletonHolder.instance;}/** * 私有构造方法 */private SingletonSample4(){}/** * 定义自己的方法 */public void singletonOperation(){}/** * 定义自己的属性 */private String singletonData;public String getSingletonData() {return singletonData;}public void setSingletonData(String singletonData) {this.singletonData = singletonData;}}6、还有种更为简洁,高效,安全的实现单例方法---通过枚举来显示单例模式。
package singleton;public enum SingletonSample5 {/** * 定义一个枚举元素,它就代表了Singleton的一个实例 */uniqueInstance;/** * 自定义方法 */public void singletonOperation(){}}
以上是单例的模式的几种不同的实现方式,与大家一同学习。
Little progress every day!
- 研磨设计模式学习笔记之单例模式
- 研磨设计模式之单例模式-1
- 研磨设计模式之单例模式-2
- 研磨设计模式之单例模式-3
- 研磨设计模式之单例模式-4
- 研磨设计模式之 单例模式-1
- 研磨设计模式之 单例模式-2
- 研磨设计模式之 单例模式-3
- 研磨设计模式之 单例模式-4
- 研磨设计模式之 单例模式-1
- 研磨设计模式之 单例模式-2
- 研磨设计模式之 单例模式-3
- 研磨设计模式之 单例模式-4
- 研磨设计模式学习笔记之装饰器模式
- 研磨设计模式之观察者模式 学习笔记
- 设计模式之单例学习笔记
- 学习笔记07-设计模式之单例设计模式
- 研磨设计模式--单例模式-内部类
- mysql
- poj2239
- INT_MIN
- GTD的几个概念
- fortran中类型
- 研磨设计模式学习笔记之单例模式
- iOS推送:实现本地推送
- ThinkRock简介
- sqldatareader
- Win7下如何硬盘安装Ubuntu
- Mealy和moore型状态机编程
- Android 系统属性SystemProperty分析
- 对话框响应WM_KEYDOWN消息
- 关于static和非static的林林总总