Перейти к основному содержимому

Что это такое

Паттерн Singleton гарантирует, что у типа есть ровно один экземпляр во всей программе, и даёт всем одну и ту же точку доступа к нему. Типичные синглтоны: конфигурация, пул соединений, логгер.

В Go для этого есть sync.Once: код инициализации внутри once.Do() выполняется ровно один раз, даже если много горутин обращаются к нему одновременно.


Пример: одна конфигурация для всех

Конфигурация загружается при первом вызове GetConfig() и больше никогда. Каждый вызывающий получает один и тот же указатель.

Загрузка один раз с помощью sync.Once

Строка «загружаем конфигурацию» печатается только один раз, хотя GetConfig() вызывается дважды, — а a == b доказывает, что оба вызывающих держат один и тот же экземпляр.

Prompt
Напишите программу на Go с синглтоном Config: функция GetConfig использует sync.Once, чтобы конфигурация загружалась ровно один раз и во время загрузки печаталась строка. Вызовите GetConfig дважды, напечатайте имя приложения и докажите, что оба вызова возвращают один и тот же экземпляр, сравнив указатели.
Вывод: программа на Go и захваченный вывод

Когда его использовать

Используйте, когда чего-то действительно должно быть ровно одно: одна загруженная конфигурация, один пул соединений, один кэш — и когда его создание дорого или дубликаты будут конфликтовать между собой.

Откажитесь, если значение можно просто создать в main() и передать тем, кому оно нужно. Явная передача зависимостей понятнее глобального доступа — синглтон это последнее средство, а не первое.


Плюсы и минусы

Плюсы: гарантированно единственный экземпляр; ленивое создание при первом обращении; безопасность при работе многих горутин благодаря sync.Once.

Минусы: это замаскированная глобальная переменная — скрытые зависимости усложняют чтение кода; в тестах его непросто подменить заглушкой; злоупотребление приводит к запутанным программам.