Gymterview
junior

Что такое паттерн Singleton?

Singleton – паттерн, гарантирующий, что у класса есть только один экземпляр, и предоставляющий глобальную точку доступа к нему.

Аналогия из жизни: Singleton – как президент страны. В один момент времени может быть только один, и все обращаются к одному и тому же человеку.

Способы реализации

Способ Ленивость Потокобезопасность Защита от reflection Простота
Enum Singleton Нет Да Да Максимальная
Static Holder (Bill Pugh) Да Да Нет Высокая
Double-Checked Locking Да Да (volatile) Нет Средняя
Примеры реализации
// 1. Enum Singleton -- рекомендуемый способ (Effective Java, Joshua Bloch)
public enum AppConfig {
    INSTANCE;

    private final Map<String, String> properties = new HashMap<>();

    public String get(String key) { return properties.get(key); }
    public void set(String key, String value) { properties.put(key, value); }
}
// Использование: AppConfig.INSTANCE.get("db.url")

// 2. Static Holder -- ленивая инициализация, потокобезопасная
public class Singleton {
    private Singleton() {}

    private static class Holder {
        static final Singleton INSTANCE = new Singleton();
    }

    public static Singleton getInstance() {
        return Holder.INSTANCE;
    }
}

// 3. Double-Checked Locking (если нужна параметризованная инициализация)
public class Singleton {
    private static volatile Singleton instance;

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

Частые ошибки

  • Double-checked locking без volatile – объект может быть частично инициализирован
  • Singleton как глобальная переменная – если нужен глобальный доступ, возможно, нужен DI
  • Singleton в многоклассовом загрузчике – каждый ClassLoader создаёт свой экземпляр

Как используется в 2026

  • Ручной Singleton редок – Spring управляет жизненным циклом бинов
  • В Spring все бины – singleton по умолчанию (управляемый контейнером)
  • Enum Singleton – для утилитных объектов вне Spring-контекста

На собеседовании: интервьюер часто просит реализовать Singleton и объяснить потокобезопасность. Назовите Enum-вариант первым – это покажет знание Effective Java. Частая ошибка – забыть volatile в DCL или не упомянуть, что Spring уже решает эту задачу.