静态内部类方式(Static Inner Class)
在 Java 中,静态内部类(Static Inner Class)方式实现单例是一种懒汉式(Lazy-Loading)+ 线程安全 + 高效的单例模式。它利用了 Java 类加载的机制,天然地保证了线程安全和单例唯一性,而且不需要加锁。
✅ 静态内部类实现单例的原理
public class Singleton {
// 私有构造函数,防止外部直接 new
private Singleton() {
System.out.println("Singleton 构造方法被调用");
}
// 静态内部类,只在调用 getInstance() 时才会加载
private static class Holder {
private static final Singleton INSTANCE = new Singleton();
}
// 对外公开获取实例的静态方法
public static Singleton getInstance() {
return Holder.INSTANCE;
}
}
✅ 为什么这种方式是线程安全且单例的?
-
类加载机制决定了线程安全性:
-
Holder是一个静态内部类,只有在getInstance()方法被调用时,Holder类才会被加载。 -
类加载过程是线程安全的,JVM 会保证类只会被加载一次,且类的初始化过程是同步的(即由 JVM 保证只有一个线程会执行类的
<clinit>静态初始化)。
-
-
延迟加载(懒加载):
-
Singleton类加载的时候不会加载Holder。 -
只有调用
getInstance()时,Holder才会加载并初始化INSTANCE,实现了延迟实例化。
-
-
不会有额外的同步锁开销:
-
不像双重检查锁(DCL)需要加锁判断,这种方式完全不需要加锁,效率更高。
-
🔁 流程示意图(简化逻辑)
调用 Singleton.getInstance()
↓
JVM 检查 Holder 是否已加载
↓
如果没有,则加载 Holder → 初始化 INSTANCE
↓
返回 Holder.INSTANCE (唯一的 Singleton 实例)
✅ 总结优点
| 特性 | 静态内部类实现方式 |
|---|---|
| 是否线程安全 | ✅ 是 |
| 是否懒加载 | ✅ 是 |
| 是否高性能 | ✅ 是(无锁) |
| 是否易读 | ✅ 是 |
| 是否可靠 | ✅ 是(推荐方式之一) |
浙公网安备 33010602011771号