静态构造函数 - c#中的单例设计模式

Tom*_*ise 1 .net c# design-patterns

如果,我用单例设计模式中的静态构造函数替换私有构造函数怎么办?

public sealed class Singleton
{
    private static Singleton instance=null;

    private Singleton()
    {
    }

    public static Singleton Instance
    {
        get
        {
            if (instance==null)
            {
                instance = new Singleton();
            }
            return instance;
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

静态构造函数只会被调用一次,我在实现中找不到任何差异.我们可以用静态构造函数替换private吗?

Jon*_*ase 6

私有构造函数在这种情况下所做的一切就是阻止类之外的任何东西实例化类Singleton的实例,这几乎肯定是故意的,因为单例只应该有一个实例.

在要使用类型或其任何静态成员之前,静态类构造函数在未知时间为类型运行一次.静态字段在运行静态构造函数之前初始化.

所以,我想你可以用静态构造函数替换构造函数,但是这会给你单例类型上的隐式无参数构造函数,这将允许任何人实例化一个实例,这可能与你使用它的原因不一致首先是单身人士模式.它也不会改变你的课程如何构建,真的,为什么呢?

例如,以下面的类为例:

public class Test { }
Run Code Online (Sandbox Code Playgroud)

在幕后,因为没有声明的构造函数,C#编译器会隐式地向该类添加无参数的公共构造函数,从而允许使用者创建实例.

public class Program {
    public static void Main() { 
        var test = new Test();
    }
}
Run Code Online (Sandbox Code Playgroud)

如果您希望能够创建您的课程,这一切都很好.单例模式旨在仅向消费者提供类型的单个实例.我们可以将这个静态实例添加到我们的测试类型中:

public class Test { public static Test Instance {get;} = new Test(); }
Run Code Online (Sandbox Code Playgroud)

我们可以像这样得到这个静态实例:

public class Program {
    public static void Main() {
        var test = Test.Instance; // good
        var other = new Test(); // less than ideal
    }
}
Run Code Online (Sandbox Code Playgroud)

所以我们正如预期的那样通过它的实例字段提供对单例对象的访问,但是我们仍然可以创建单例类型的实例,这不太好,因为它违背了单例的目的(即,只有一个共享)实例.)

所以我们在类型中添加一个私有的无参数构造函数.

public class Test { 
    private Test() {}
    public static Test Instance {get;} = new Test(); 
}
Run Code Online (Sandbox Code Playgroud)

将构造函数添加到类型将导致C#编译器不添加隐式的无公共参数构造函数.将其设为私有允许在类范围内访问它,该范围用于实例化我们的实例属性,并防止其他任何实例化对象.最终结果是:

public class Program {
    public static void Main() {
        var test = Test.Instance; // good
        var other = new Test(); // Compile time error
    }
}
Run Code Online (Sandbox Code Playgroud)

您的单例对象现在可以防止实例化该类的其他实例,并且使用它的唯一方法是按预期通过实例属性.