单例模式
来源:互联网 发布:淘宝评价中心 编辑:程序博客网 时间:2024/04/28 01:47
注意点
- 单例类只能有一个实例
- 单例类必须自己创建自己的唯一实例
- 单例类必须给所有其他对象提供这一实例
优点
- 在内存里只有一个实例,减少了内存的开销,尤其是频繁的创建和销毁实例
- 避免对资源的多重占用
缺点
- 没有接口,不能继承,与单一职责原则冲突,一个类应该只关心内部逻辑,而不关心外面怎么样来实例化
懒汉、线程不安全(不支持线程安全)
- 描述:
- 这种方式是最基本的实现方式,这种实现最大的问题就是不支持多线程。因为没有加锁synchronized,所以严格意义上它并不算单例模式
public class Singleton { private static Singleton singleton; //让构造函数为 private,这样该类就不会被实例化 private Singleton() { } //获取唯一可用的对象 public static Singleton getInstance(){ if (singleton == null) { singleton = new Singleton(); } return singleton; } public void TestSingleton() { System.out.println("单例模式-懒汉、线程不安全"); }}
public class SingletonDemo { public static void main(String[] args) { //不合法的构造函数 //编译时错误:构造函数 SingleObject() 是不可见的 //SingleObject object = new SingleObject(); //获取唯一可用的对象 Singleton singleton = Singleton.getInstance(); singleton.TestSingleton(); }}
懒汉、线程安全
- 描述:
- 这种方式具备很好的 lazy loading,能够在多线程中很好的工作,但是,效率很低,99% 情况下不需要同步
- 优点:
- 第一次调用才初始化,避免内存浪费
- 缺点:
- 必须加锁 synchronized 才能保证单例,但加锁会影响效率
- getInstance() 的性能对应用程序不是很关键(该方法使用不太频繁)
public class SingletonSafety { private SingletonSafety(){} private static SingletonSafety singletonSafety; public static synchronized SingletonSafety getInstance(){ if (singletonSafety == null) { singletonSafety = new SingletonSafety(); } return singletonSafety; } public void TestSingletonSafety() { System.out.println("单例模式-懒汉、线程安全"); }}
饿汉
- 描述:
- 这种方式比较常用,但容易产生垃圾对象
- 优点:
- 没有加锁,执行效率会提高
- 缺点:
- 类加载时就初始化,浪费内存
public class SingletonHungry { private SingletonHungry() {} private static SingletonHungry singletonHungry = new SingletonHungry(); public static SingletonHungry getInstance() { return singletonHungry; } public void TestSingletonHungry() { System.out.println("单例模式-饿汉"); }}
双检锁/双重校验锁(DCL,即 double-checked locking)
- 描述
- 这种方式采用双锁机制,安全且在多线程情况下能保持高性
- getInstance() 的性能对应用程序很关键
public class SingletonDCL { private SingletonDCL(){} private volatile static SingletonDCL singletonDCL; public static SingletonDCL getInstance() { if (singletonDCL == null) { synchronized (SingletonDCL.class) { if (singletonDCL == null) { singletonDCL = new SingletonDCL(); } } } return singletonDCL; } public void TestSingletonDCL() { System.out.println("单例模式-双检锁/双重校验锁(DCL,即 double-checked locking)"); }}
登记式/静态内部类
- 描述:
- 这种方式能达到双检锁方式一样的功效,但实现更简单。对静态域使用延迟初始化,应使用这种方式而不是双检锁方式。这种方式只适用于静态域的情况,双检锁方式可在实例域需要延迟初始化时使用。
public class SingletonStatic { private SingletonStatic() {} private static class SingletonHolder{ private static final SingletonStatic SINGLETON_STATIC = new SingletonStatic(); } public static final SingletonStatic getInstance() { return SingletonHolder.SINGLETON_STATIC; } public void TestSingletonStatic() { System.out.println("单例模式-登记式/静态内部类"); }}
阅读全文
1 0
- 单例、单例模式
- 单例模式-多线程单例模式
- 单件模式(单例模式)
- 设计模式------单例模式
- 设计模式------单例模式
- 设计模式-单例模式
- 设计模式 - 单例模式
- 设计模式---单例模式
- 设计模式---单例模式
- PHP模式-单例模式
- 【设计模式】单例模式
- 设计模式-单例模式
- 设计模式----单例模式
- 设计模式--单例模式
- 设计模式-单例模式
- 单例模式(单子模式)
- 设计模式-单例模式
- [设计模式] 单例模式
- IndiaHacks 2nd Elimination 2017 B
- mysql主从复制
- hibernate注解
- 【Docker】docker创建测试环境的伪分布式Redis集群
- windows 下sftp ssh自动脚本
- 单例模式
- 用源码安装的apache替代原来的apache
- WindowManager和WindowManager.LayoutParams的使用以及实现悬浮窗口的方法
- SpringMvc+Tomcat+Angular4 部署运行
- 2017.03.29.腾讯openday
- list去除重复
- js高级教程阅读笔记 第五章-引用类型(5.6)
- oracle忘记密码sys密码怎么改
- 电脑加域、exchange邮箱设置、绑定打印机