版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/u012292754/article/details/87873758
1 单例设计模式
/*
* 自己定义的类,默认情况下,外界代码可以随意创建多个实例,但是有些时候,不希望外界随意创建实例,
* 在整个程序运行期间,只有一个实例
*
* 实现单例模式,要点:
* 1. 类的构造方法必须是 private
*
* 2. 外界代码要获取类的实例,不能够随意创建,只能通过调用类的静态方法去获取类的实例;
*
* 3. 所以类必须有一个静态方法,getInstance(),来提供获取唯一实例的功能
* getInstance()方法,必须保证类的实例创建,且仅创建一次,返回唯一实例
*
* 单例模式应用场景?
* 1. 配置管理组件,可以在读取大量的配置信息之后,将配置信息仅仅保存在一个实例的实例变量中,这样可以避免
* 对于静态不变的配置信息,反复多次的读取;
*
* 2. JDBC辅助组件,全局只有一个实例,实例中持有了一个内部的简单数据源
* 使用了单例模式之后,就保证了只有一个实例,那么数据源也只有一个,不会重复创建多次数据源(数据库连接池)
*
*
* */
public class Singleton {
// 首先必须有一个私有的静态变量,来引用即将被创建出来的单利
private static Singleton instance = null;
/*
* 其次,必须对自己的构造方法使用 private 进行私有化
*
* */
private Singleton() {
}
/*
* 最后,需要一个共有的,静态方法
* 这个方法负责创建唯一的实例,并且返回这个唯一的实例
*
* 必须考虑到可能出现的多线程并发访问安全的问题
* 就是说,可能会有多个线程同时过来获取单例,可能会导致创建多次单例
* 所以这个方法要进行多线程并发访问安全的控制
*
*
* 对于多线程的并发访问安全控制,最简单的是就是在方法上加上 synchronized 关键词
* public static synchronized Singleton getInstance() 方法
* 但是这样做有很大的问题:在第一次调用的时候,的确可以做到避免多个线程并发访问创建多个实例
* 但是在第一次创建完实例以后,就会出现以后的多个线程并发访问这个方法的时候,就会在方法级别进行同步
* 导致并发性能大幅度降低
*
*
* */
public static Singleton getInstance() {
// 两步检查机制
// 1. 多个线程过来的时候,判断 instance 是否为 null
// 如果为 null 再往下走
if (instance == null) {
// 在这里,进行多个线程的同步
// 同一时间,只能有一个线程获取到 Singleton Class 对象的锁
synchronized (Singleton.class) {
if (instance == null) {
instance = new Singleton();
}
}
}
return instance;
}
}