《C# in Depth: Implementing the Singleton Pattern》這篇文章定義了很多種方式,我就采用Lazy方式了。
public sealed class Singleton
{
private static readonly Lazy<Singleton> lazy =
new Lazy<Singleton>(() => new Singleton());
public static Singleton Instance { get { return lazy.Value; } }
private Singleton()
{
}
}
根據(jù)官方文檔《Microsoft's Lazy Initialization documentation》,Lazy對象是線程安全的:
By default, Lazy objects are thread-safe. That is, if the constructor does not specify the kind of thread safety, the Lazy<T> objects it creates are thread-safe. In multi-threaded scenarios, the first thread to access the Value property of a thread-safe Lazy<T> object initializes it for all subsequent accesses on all threads, and all threads share the same data. Therefore, it does not matter which thread initializes the object, and race conditions are benign.
無法實現(xiàn)Generic Singleton
根據(jù)Andrew Hare的解釋,無法實現(xiàn)泛型單件模式:
The problem with a generic singleton factory is that since it is generic you do not control the "singleton" type that is instantiated so you can never guarantee that the instance you create will be the only instance in the application.
If a user can provide a type to as a generic type argument then they can also create instances of that type. In other words, you cannot create a generic singleton factory - it undermines the pattern itself.
AndreasN說,Creating a singleton class is just a few lines of code, and with the difficulty of making a generic singleton i always write those lines of code.
public class Singleton
{
private Singleton() {}
static Singleton() {}
private static Singleton _instance = new Singleton();
public static Singleton Instance { get { return _instance; }}
}
The
private static Singleton _instance = new Singleton();
line removes the need for locking, as a static constructor is thread safe.