原文:@程序员小灰
单例模式第一版
1
2
3
4
5
6
7
8
9
10
11
public class Singleton {
private Singleton() {} //私有构造函数
private static Singleton instance; //单例对象
//静态工厂方法
public static Singleton getInstance() {
if (instance == null) {
instance = new Singleton();
}
return instance;
}
}
单例模式第二版
在第一版的基础上加上双重加锁检测,防止并发时候创建多个对象
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
public class Singleton {
private Singleton() {} //私有构造函数
private static Singleton instance = null; //单例对象
//静态工厂方法
public static Singleton getInstance() {
if (instance == null) { //双重检测机制
synchronized (Singleton.class){ //同步锁
if (instance == null) { //双重检测机制
instance = new Singleton();
}
}
}
return instance;
}
}
单例模式第三版
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
public class Singleton {
private Singleton() {} //私有构造函数
private volatile static Singleton instance = null; //单例对象
//静态工厂方法
public static Singleton getInstance() {
if (instance == null) { //双重检测机制
synchronized (Singleton.class){ //同步锁
if (instance == null) { //双重检测机制
instance = new Singleton();
}
}
}
return instance;
}
}
volatile:防止指令重排,是很有必要的,instance = new Singleton();这段代码其实分为三部执行:
- 为 instance 分配内存空间;
- 初始化 instance;
- 将 instance 指向分配的内存地址;
如果不添加 volatile ,执行顺序有可能变成 1->3->2,在多线程环境下就容易出问题。
单例模式第四版(推荐使用)
利用ClassLoader的加载机制来实现懒加载,并保证构建的单例线程安全。
1
2
3
4
5
6
7
8
9
public class Singleton {
private static class LazyHolder {
private static final Singleton INSTANCE = new Singleton();
}
private Singleton (){}
public static Singleton getInstance() {
return LazyHolder.INSTANCE;
}
}