一、单例模式
大部分时候,我们都把类的构造器定义成public访问权限,运行任何类自由创建该类的对象,但是在某些时候,允许其他类自由的创建该类的对象是没有任何意义的。还有可能造成系统性能下降,例:某个系统只有一个窗口管理器,此时在系统中创建多个对象其实没有任何意义的。
如果一个类始终只能创建一个实例,则这个类被称为单例类,这样的模式被称为单例模式
二、单例模式的几种实现
1、饿汉式
/**
* 单例模式-饿汉式
*/
public class Singleton {
private static Singleton1 instance = new Singleton();
private Singleton(){}
//基于classloader 加载机制。避免了多线程同步的问题,但是容易产生垃圾对象
public static Singleton getInstance() {
return instance;
}
}
2、懒汉式(线程不安全)
/**
* 单例模式-懒汉式(线程不安全)
*/
public class Singleton {
//使用一个类变量缓存曾经创建的实例
private static Singleton singleton;
//使用private 对构造器进行私有化
private Singleton(){}
//提供静态方法,用于返回Singleton实例,保证只产生一个Singleton对象
public static Singleton getInstance() {
//如果没有创建,则创建一个实例,存在则直接返回
if(singleton==null){
singleton = new Singleton();
}
return singleton;
}
public static void main(String[] args) {
Singleton singleton = Singleton.getInstance();
Singleton singleton1 = Singleton.getInstance();
//对比创建的Singleton实例,返回为true
System.out.println(singleton==singleton1);
}
}
3、懒汉式(线程安全)
/**
* 单例模式-懒汉式(线程安全),在懒汉式上进行优化,保证在多线程状态下,进行加锁,但是也影响了效率
*/
public class Singleton {
//使用一个类变量缓存曾经创建的实例
private static Singleton singleton;
//使用private 对构造器进行私有化
private Singleton(){}
//提供静态方法,用于返回Singleton实例,保证只产生一个Singleton对象
public static synchronized Singleton getInstance() {
//如果没有创建,则创建一个实例,存在则直接返回
if(singleton==null){
singleton = new Singleton();
}
return singleton;
}
}
4、双检锁/双重校验锁
/**
* 双检锁/双重校验锁
*/
public class Singleton {
//volatile 保证有效性与可见性
private volatile static Singleton singleton;
private Singleton (){}
public static Singleton getSingleton() {
if (singleton == null) {
synchronized (Singleton.class) {
if (singleton == null) {
singleton = new Singleton();
}
}
}
return singleton;
}
}
5、静态内部类
public class Singleton {
private Singleton() {}
private static class SingletonInstance {
private static final Singleton INSTANCE = new Singleton();
}
public static Singleton getInstance() {
return SingletonInstance.INSTANCE;
}
}
三、总结
在开发过程中,尽量使用线程安全,延迟加载,效率较高的单例模式。