Sobes.tech
Назад к вопросам
Middle — Middle+
67

Какими способами обеспечивается потокобезопасность при реализации паттерна Singleton?

Ответ от нейросети

sobes.tech AI

Потокобезопасность при реализации паттерна Singleton в Java достигается несколькими способами:

  1. Использование synchronized

    Метод получения экземпляра помечается ключевым словом synchronized, чтобы обеспечить эксклюзивный доступ:

    public class Singleton {
        private static Singleton instance;
        private Singleton() {}
        public static synchronized Singleton getInstance() {
            if (instance == null) {
                instance = new Singleton();
            }
            return instance;
        }
    }
    

    Недостаток — накладные расходы на синхронизацию при каждом вызове.

  2. Double-checked locking

    Проверка экземпляра происходит дважды — до и после синхронизации, чтобы снизить накладные расходы:

    public class Singleton {
        private static volatile Singleton instance;
        private Singleton() {}
        public static Singleton getInstance() {
            if (instance == null) {
                synchronized (Singleton.class) {
                    if (instance == null) {
                        instance = new Singleton();
                    }
                }
            }
            return instance;
        }
    }
    

    Ключевое слово volatile гарантирует корректную работу с памятью.

  3. Использование статического внутреннего класса (Initialization-on-demand holder idiom)

    Этот способ ленивой и потокобезопасной инициализации не требует синхронизации:

    public class Singleton {
        private Singleton() {}
        private static class Holder {
            private static final Singleton INSTANCE = new Singleton();
        }
        public static Singleton getInstance() {
            return Holder.INSTANCE;
        }
    }
    

    Класс Holder загружается и инициализируется только при первом вызове getInstance().

  4. Enum Singleton

    Использование перечисления гарантирует потокобезопасность и защиту от сериализации:

    public enum Singleton {
        INSTANCE;
        // методы
    }
    

Каждый из этих способов обеспечивает потокобезопасность, выбор зависит от требований к производительности и удобству.