MST
星途 面试题库

面试题:Java双重检查锁定单例模式在高并发场景下的优化

假设在一个高并发的Java应用中使用双重检查锁定单例模式,由于频繁的实例检查和创建可能会带来性能瓶颈。请提出至少两种优化方案,并详细说明每种方案的原理和适用场景。
38.8万 热度难度
编程语言Java

知识考点

AI 面试

面试题答案

一键面试

方案一:静态内部类实现单例

  1. 原理
    • 利用Java类加载机制,静态内部类只有在被使用时才会加载。当外部类被加载时,静态内部类不会被立即加载。只有当调用 getInstance 方法时,静态内部类 Holder 才会被加载,此时会初始化 INSTANCE 实例。由于类加载过程是线程安全的,所以这种方式保证了单例的线程安全性,并且延迟了实例的创建。
    • 示例代码如下:
public class Singleton {
    private Singleton() {}
    private static class Holder {
        private static final Singleton INSTANCE = new Singleton();
    }
    public static Singleton getInstance() {
        return Holder.INSTANCE;
    }
}
  1. 适用场景:适用于大多数高并发场景,尤其是需要延迟加载单例实例的情况。由于类加载机制的保证,这种方式既简单又高效,无需额外的同步操作。

方案二:枚举实现单例

  1. 原理
    • Java中的枚举类型在编译时就创建好了所有的枚举实例,并且枚举实例的创建是线程安全的。通过定义一个枚举类型,其只有一个实例,就可以实现单例模式。枚举类型在反序列化时,不会重新创建新的实例,而是返回已有的枚举实例,天然防止了反序列化破坏单例。
    • 示例代码如下:
public enum Singleton {
    INSTANCE;
    // 可以添加其他业务方法
    public void doSomething() {
        // 业务逻辑
    }
}
  1. 适用场景:适用于需要防止反序列化破坏单例以及需要简洁实现单例的场景。在高并发环境下,枚举实现的单例性能很好,并且代码简洁,无需额外的同步或复杂逻辑。它是实现单例模式的最佳实践之一,尤其适合应用于需要序列化和反序列化的场景。