单例类保证一个类全局仅有一个实例,并提供一个全局访问点,因为只能生成一个实例,所以咱们必须把构造函数设为私有函数以禁止他人建立实例。html
该实现没有额外开销,不要求线程安全的状况下能够使用:程序员
public class Singleton1 { private static Singleton1 instance = null; private Singleton1() { } public static Singleton1 Instance { get { if (instance == null) { instance = new Singleton1(); } return instance; } } }
因为每次访问单例类实例都会加锁,而加锁是一个很是耗时的操做,故不推荐使用:c#
public class Singleton2 { private readonly static object lockObj = new object(); private static Singleton2 instance = null; private Singleton2() { } public static Singleton2 Instance { get { lock(lockObj) { if (instance == null) { instance = new Singleton2(); } } return instance; } } }
写法简单,线程安全,但构造时机不是由程序员掌控的:安全
public class Singleton3 { private static Singleton3 instance = new Singleton3(); private Singleton3() { } public static Singleton3 Instance { get { return instance; } } public static void Test() { Console.WriteLine("test"); } }
当.NET运行时发现第一次使用Singleton3时会建立单例的实例,而不是在第一次调用Singleton3.Instance属性时建立,如进行如下操做:函数
Singleton3.Test();
在实现2的基础上进行改进,只在第一次建立实例时加锁,提升访问性能:性能
public class Singleton4 { private readonly static object lockObj = new object(); private static Singleton4 instance = null; private Singleton4() { } public static Singleton4 Instance { get { if (instance == null) { lock (lockObj) { if (instance == null) { instance = new Singleton4(); } } } return instance; } } }
在方法3的基础上进行改进,确保只有访问Singleton5.Instance属性时才会构造实例:.net
public class Singleton5 { class Nested { internal static readonly Singleton5 instance = new Singleton5(); } private Singleton5() { } public static Singleton5 Instance { get { return Nested.instance; } } }
经过单例基类,咱们能够简单的经过继承建立一个单例类,实现代码复用:线程
// 因为单例基类不能实例化,故设计为抽象类 public abstract class Singleton<T> where T : class { // 这里采用实现5的方案,实际可采用上述任意一种方案 class Nested { // 建立模板类实例,参数2设为true表示支持私有构造函数 internal static readonly T instance = Activator.CreateInstance(typeof(T), true) as T; } private static T instance = null; public static T Instance { get { return Nested.instance; } } }
使用方法以下:设计
class TestSingleton : Singleton<TestSingleton> { // 将构造函数私有化,防止外部经过new建立 private TestSingleton() { } }
一、《剑指offer》code
二、http://www.runoob.com/design-pattern/singleton-pattern.html