在Java中实现线程安全的单例模式有多种方法,每种方法都有其优点和适用场景。下面介绍几种常见且易于理解的实现方式,并结合代码示例进行说明。
1. 饿汉式(Eager Initialization)
最简单、最直观的方式是直接在类加载时就实例化对象。由于类加载是线程安全的,保证了单例的唯一性。
public class SingletonEager {
// 直接实例化,类加载时完成
private static final SingletonEager INSTANCE = new SingletonEager();
// 私有构造函数,防止外部实例化
private SingletonEager() {}
public static SingletonEager getInstance() {
return INSTANCE;
}
}
优点:实现简单,线程安全。
缺点:类加载时就实例化,若单例对象比较重且在某些项目中可能不需要,导致资源浪费。
2. 懒汉式(Lazy Initialization)+ synchronized
通过在第一次调用 getInstance() 时才实例化对象,并使用 synchronized 关键字保证线程安全。
public class SingletonLazySync {
private static SingletonLazySync instance;
private SingletonLazySync() {}
public static synchronized SingletonLazySync getInstance() {
if (instance == null) {
instance = new SingletonLazySync();
}
return instance;
}
}
优点:延迟加载。
缺点:每次调用都要进入同步块,性能不佳。
3. 双重检查锁(Double-Check Locking, DCL)
通过两次检查 instance 是否为 null,在第一次进入同步块时才实例化,从而减少同步的开销。
public class SingletonDCL {
// volatile 关键字保证可见性和防止指令重排
private static volatile SingletonDCL instance;
private SingletonDCL() {}
public static SingletonDCL getInstance() {
if (instance == null) { // 第一重检查
synchronized (SingletonDCL.class) {
if (instance == null) { // 第二重检查
instance = new SingletonDCL();
}
}
}
return instance;
}
}
优点:延迟加载且性能较好。
缺点:代码相对复杂,需要 volatile。
4. 静态内部类(Initialization-on-demand Holder)
利用 Java 的类加载机制,只有在第一次访问 Holder.INSTANCE 时才加载内部类,从而实现延迟加载且线程安全。
public class SingletonHolder {
private SingletonHolder() {}
// 静态内部类,只有在首次访问时才加载
private static class Holder {
private static final SingletonHolder INSTANCE = new SingletonHolder();
}
public static SingletonHolder getInstance() {
return Holder.INSTANCE;
}
}
优点:延迟加载、线程安全且实现最简洁。
缺点:对 Java 语言规范有一定依赖,若使用 JDK 1.4 以前的版本需注意。
5. 枚举实现(Enum Singleton)
Java 枚举天然具有单例性质,且在序列化和反射方面更安全。
public enum SingletonEnum {
INSTANCE;
public void someMethod() {
// 实例方法
}
}
优点:最简洁、最安全,天然防止反射和序列化攻击。
缺点:不适合需要延迟初始化或需要继承的情况。
小结
- 饿汉式:实现最简单,适合资源占用少且不关心延迟的问题。
- 懒汉式 + synchronized:延迟加载,但同步开销大。
- 双重检查锁:兼顾延迟与性能,但实现稍显复杂。
- 静态内部类:延迟加载、线程安全、实现简洁,推荐使用。
- 枚举:最安全、最简洁,适用于不需要延迟加载的场景。
根据项目需求和资源约束,选择合适的实现方式即可。祝编码愉快!

发表回复