Шаблон Singleton с открытым конструктором - PullRequest
3 голосов
/ 16 сентября 2009
public class MySingletonClass
{
  public MySingletonClass()
  {
    _mySingletonObj = Instance();
  }

  public static MySingletonClass Instance()
  {
    if (_mySingletonObj  == null)
    {
      lock (typeof(lockObject))
      {
        if (_mySingletonObj  == null)
          _mySingletonObj  = new MySingletonClass();
      }
    }
    return _mySingletonObj ;
  }
}

MySingletonClass _myObj = new MySingletonClass();

Это действует как синглтон с публичными конструкторами ..?

Спасибо

Ответы [ 6 ]

14 голосов
/ 16 сентября 2009

Нет, это не синглтон - каждый может создать несколько его экземпляров. (Оставляя в стороне проблему переполнения стека, которая уже была поднята, и тот факт, что вы используете двойную проверку блокировки небезопасно.)

Одной из отличительных особенностей одноэлементного типа является то, что он предотвращает создание более одного экземпляра самого себя.

Из википедии Шаблон Singleton Артикул:

В разработке программного обеспечения, синглтон шаблон это шаблон дизайна, который используется для ограничения реализации класс для одного объекта.

Из хранилище шаблонов Уорда Каннингема :

Синглтон - это комбинация двух Основные свойства:

  • Убедитесь, что у класса есть только один экземпляр
  • Предоставить глобальную точку доступа к ней

Очевидно, ваш синглтон не соответствует обоим этим определениям.

См. Мою единственную статью для реальных реализаций.

4 голосов
/ 16 сентября 2009

Отправленный код не работает как одиночный, из-за общедоступного конструктора, но в дополнение к этому, существуют многочисленные недостатки и проблемы с кодом:

  • Открытый конструктор вызывает Instance, который вызывает открытый конструктор, который вызывает Instance, который вызывает ..... переполнение стека неизбежно
  • Открытый конструктор возвращает новый объект каждый раз, когда он вызывается, вы не можете заменить возвращенный результат той же ссылкой на объект при последующих запросах. Другими словами, публичный конструктор в синглтоне нарушает шаблон.
  • Вы не должны пропускать ваши объекты блокировки, которые в вашем случае вы блокируете по типу объекта. Не делайте этого, вместо этого блокируйте частный объект.

Вот исправленная версия вашего кода:

public class MySingletonClass
{
  private readonly object _mySingletonLock = new object();
  private volatile MySingletonClass _mySingletonObj;

  private MySingletonClass()
  {
    // normal initialization, do not call Instance()
  }

  public static MySingletonClass Instance()
  {
    if (_mySingletonObj == null)
    {
      lock (_mySingletonLock)
      {
        if (_mySingletonObj  == null)
          _mySingletonObj = new MySingletonClass();
      }
    }
    return _mySingletonObj;
  }
}

MySingletonClass _myObj = MySingletonClass.Instance();
3 голосов
/ 16 сентября 2009

Ознакомьтесь с разделом по оптимизированному коду .NET в Dofactory . Это ИМО лучшая реализация. Также проверьте сайт для других реализаций шаблонов проектирования в C #.

1 голос
/ 16 сентября 2009

Вместо блокировки вы также можете попытаться создать статический синглтон только для чтения ...

public sealed class Singleton
{
    private static readonly Singleton instance = new Singleton();

    static Singleton()
    {
    }

    private Singleton()
    {
    }

    /// <summary>
    /// The public Instance property to use
    /// </summary>
    public static Singleton Instance
    {
        get { return instance; }
    }
}
1 голос
/ 16 сентября 2009

Конструктор должен быть приватным

0 голосов
/ 01 июля 2012

Суть Singleton заключается в том, чтобы обеспечить:

  • ровно один экземпляр класса в системе;
  • простой доступ к нему.

Реализация Singleton основана на создании класса с методом (или свойством в .NET), который создает экземпляр этого класса, если он еще не существует. Конструктор класса должен быть закрытым, чтобы предотвратить другие способы инициализации. Также Singleton необходимо бережно использовать в многопоточных приложениях, потому что в один момент времени два потока могут создавать два разных экземпляра (что нарушает шаблон singleton).

Более подробную информацию и примеры вы можете найти здесь.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...