[Head First设计模式]一个人的平安夜——单例模式
系列文章
[Head First设计模式]山西面馆中的设计模式——装饰者模式
[Head First设计模式]山西面馆中的设计模式——观察者模式
[Head First设计模式]山西面馆中的设计模式——建造者模式
[Head First设计模式]饺子馆(冬至)中的设计模式——工厂模式
引言
已经不想再数这是第多少个一个人的平安夜了,一个人走在路上,发现满脑子的技术问题,也许,在技术中才能找到一点安慰吧。很多朋友一直问我,为什么那么拼,lz只是觉得“如果连自己喜欢的工作,都做不好,那么活着就太空虚了,男人么就应该对自己恨一点。如果你现在没有得到你想要的生活,只能说明你对自己还不够狠”。言归正传,说说今天的单例模式。
单例模式定义
单例模式是一种常用的软件设计模式。在它的核心结构中只包含一个被称为单例类的特殊类。通过单例模式可以保证系统中一个类只有一个实例而且该实例易于外界访问,从而方便对实例个数的控制并节约系统资源。如果希望在系统中某个类的对象只能存在一个,单例模式是最好的解决方案。
大家都知道“一夫一妻制”,在中国,一个男人,有且只能有一个媳妇,如果你非要找个小三,势必会增加开销,占用更多资源。所以没资本的屌丝们,劝你们,媳妇这个对象有且只能创建一个,如果你不自量力,非要整个小三出来,像某某官员,一般不会出问题,但当小三和你媳妇争夺资源的时,势必会出现致命性的bug,信不信由你?
单例模式类图
(类图来自:http://www.cnblogs.com/zhili/p/SingletonPatterm.html,这里借用一下)
实现单例模式条件
通过观察上面类图可知:
1.静态的私有化字段;
private static readonly Singleton uniqueInstance = new Singleton();
2.私有构造器
private Singleton(){ }
3.提供公共的访问该类实例的方法.
1 public static Singleton GetInstance() 2 { 3 return uniqueInstance; 4 }
常见的单例模式
一,饿汉式
1 public sealed class Singleton 2 { 3 #region 饿汉式 4 private static readonly Singleton uniqueInstance = new Singleton(); 5 private Singleton() { } 6 public static Singleton GetInstance() 7 { 8 return uniqueInstance; 9 } 10 #endregion 11 }
优点:
1.线程安全
2.在类加载的同时已经创建好一个静态对象,调用时反应速度快。
3.通过sealed修饰类,阻止派生类的出现,因为派生可能会增加实例。
缺点:
资源效率不高,可能GetInstance()永远不会执行到,但执行该类的其他静态方法或者加载了该类(class.forName),那么这个实例仍然初始化。
二,懒汉式
1 public sealed class Singleton 2 { 3 private static Singleton instance; 4 //程序运行时创建一个静态的只读对象 5 private static readonly object o = new object(); 6 private Singleton() { } 7 public static Singleton GetInstance() 8 { 9 //双重锁 10 //先判断实例是否存在,不存在再加锁处理 11 //这样不用让线程每次都加锁,保证了线程安全,也提高了性能 12 if (instance == null) 13 { 14 //保证只有一个线程 15 lock (o) 16 { 17 ///若实例不存在,则new一个新实例,否则返回已有的实例 18 if (instance == null) 19 { 20 instance = new Singleton(); 21 } 22 } 23 } 24 return instance; 25 } 26 }
懒汉式面临线程安全的问题,通过双重锁定这样的处理才可以保证安全。
测试
1 class Program 2 { 3 static void Main(string[] args) 4 { 5 Singleton singleton1 = Singleton.GetInstance(); 6 Singleton singleton2 = Singleton.GetInstance(); 7 if (singleton1==singleton2) 8 { 9 Console.WriteLine("两个对象一样"); 10 } 11 Console.Read(); 12 } 13 }
结果
本打算创建个对象,给我买个苹果的,看来两个对象一样,也只能自己给自己买了。
总结
单例模式(Singleton),保证一个类仅有一个实例,并提供一个访问它的全局访问点。