保證一個類僅有一個實例,並提供一個該實例的全局訪問點。 --《設計模式GoF》數據庫
1,初始版本設計模式
namespace DesignPatternDemo.ConsoleApp { /// <summary> /// 單例類 /// </summary> public class Singleton { private static Singleton _singleton; private Singleton() { } public static Singleton GetInstance() { if (_singleton== null) { _singleton = new Singleton(); } return _singleton; } } }
注意:此版本在多線程環境下不能保證線程安全!安全
2,雙檢鎖多線程
namespace DesignPatternDemo.ConsoleApp { /// <summary> /// 單例類(雙檢鎖) /// </summary> public class SingletonV2 { private static SingletonV2 _singleton; private static readonly object lockObj = new object(); private SingletonV2() { } public static SingletonV2 GetInstance() { if (_singleton == null) { lock (lockObj) { if (_singleton == null) { _singleton = new SingletonV2(); } } } return _singleton; } } }
總結:雙檢鎖版本解決了多線程環境下線程安全的問題。測試
3,餓漢式版本spa
namespace DesignPatternDemo.ConsoleApp { /// <summary> /// 單例類(餓漢式版本) /// </summary> public class SingletonV3 { private static readonly SingletonV3 _singleton = new SingletonV3(); private SingletonV3() { } public static SingletonV3 GetInstance() { return _singleton; } } }
總結:這個版本的優勢是實現簡單而且沒有加鎖執行效率高,缺點是類加載時就初始化,可能會浪費內存資源。線程
4,測試設計
namespace DesignPatternDemo.ConsoleApp { class Program { static void Main(string[] args) { SingletonV2 singleton1 = SingletonV2.GetInstance(); SingletonV2 singleton2 = SingletonV2.GetInstance(); if (singleton1 == singleton2) { Console.WriteLine("對象singleton1和對象singleton2是同一個對象!"); } Console.ReadKey(); } } }
運行結果:3d