欢迎您访问365答案网,请分享给你的朋友!
生活常识 学习资料

设计模式-单例模式

时间:2023-07-08
单列模式的定义:

单例模式确保某个类只有一个实例,而且自行实例化并向整个系统提供这个实例.在计算机系统中,线程池,缓存,日志对象,对话框等常被设计成单例

单例模式的特点:

1.单例类智能有一个实例.

2.单例类必须自己创建自己的唯一实例.

3.单例类必须给其他对象提供这一实例.

实现单列的5种方式 懒汉式:默认不会实例化,第一次使用的时候实例化.(可能会由有线程安全问题) 1. 双重检查,已解决线程安全问题【推荐使用】

public class Singleton4 { private static volatile Singleton4 singleton; private Singleton4() { } public static Singleton4 getInstance() { if (singleton == null) { synchronized (Singleton4.class) { if (singleton == null) { singleton = new Singleton4(); } } } return singleton; }}

2.静态内部类  【推荐使用】

public class Singleton5 { private Singleton5() { } // 静态内部类 public static class Singleton5Instance { private static final Singleton5 INSTANCE = new Singleton5(); } public static Singleton5 getInstance() { return Singleton5Instance.INSTANCE; }}

饿汉式 : 默认实例化 (类加载的时候实例化 无线程安全问题) 1.静态常量【可用】

public class Singleton { private final static Singleton INSTANCE = new Singleton(); private Singleton() {} public static Singleton getInstance() { return INSTANCE; }}

2.静态代码块【可用】

public class Singleton2 { private static Singleton2 INSTANCE; private Singleton2() { } static { INSTANCE = new Singleton2(); } public static Singleton2 getInstance() { return INSTANCE; }}

 3.枚举【推荐使用】

public class Singleton6 { public Singleton6() { } public static Singleton6 getInstance() { return SingletonEnum.INSTANCE.getSingleton(); } private enum SingletonEnum { INSTANCE; private Singleton6 singleton; SingletonEnum() { singleton = new Singleton6(); } private Singleton6 getSingleton() { return singleton; } }}

 单例模式的破坏以及解决办法 (反射/反序列化)

 除枚举外,其他的方法都可以通过反射的方式破坏单例模式 反射是通过调用构造方法生成新的对象,如果想要阻止单例被破坏,可以在构造方法中进行判断.

private Singleton4() { if (singleton != null) { throw new RuntimeException("实例已经存在,请通过 getInstance()方法获取"); } }

如果单例类实现了Serializable, 就可以通过反序列化破坏单例.解决办法是在单例类中添加反序列化方法readResolve

public class Singleton5 { private Singleton5() { } // 静态内部类 public static class Singleton5Instance { private static final Singleton5 INSTANCE = new Singleton5(); } public static Singleton5 getInstance() { return Singleton5Instance.INSTANCE; } // 防止反序列化破坏单例模式 public Object readResolve() { return Singleton5Instance.INSTANCE; }}

添加readResolve 方法,方法中返回实例的逻辑与单例类提供的获取实例的逻辑一模一样.

Copyright © 2016-2020 www.365daan.com All Rights Reserved. 365答案网 版权所有 备案号:

部分内容来自互联网,版权归原作者所有,如有冒犯请联系我们,我们将在三个工作时内妥善处理。