模式分类:
从目的来看:
1.创建型(Creational)模式:负责对象创建。
2.结构型(Structural)模式:处理类于对象间的组合。
3.行为型(Behavioral)模式:类与对象交互中的职责分配。
从范围看:
1.类模式处理类于子类的静态关系。
2.对象模式处理对象间的动态关系。
动机
在软件系统中,经常有一些这样特殊的类,必须保证他们在系统中只存在一个实例,才能确保他们的逻辑正确性、以及良好的效率。
绕过常规的构造器,提供一种机制保证一个类只有一个实例。
意图
保证一个类仅有一个实例,并提供一个该实例的全局访问点。
结构
单线程Singleton模式实现:
public class Singleton { private static Singleton Instance; private Singleton() {} public static Singleton Instance { get { if(instance == null) { instance = new Singleton(); } return instance; } } }
或者:
public class Singleton { private static Singleton Instance = new Singleton(); private Singleton() {} public static Singleton Instance { get { return instance; } } }
两者有啥区别?
第一种可以做到LazyLoad。
判断对象的引用:
Object.ReferenceEquals(t1,t2)
单线程Singleton模式的几个要点
1.单例模式可以设置为protected允许派生子类。
2.单例模式一般不支持ICloneable接口,这可以导致多个实例,于单例模式初衷违背。
3.单例模式不要支持序列化,序列化,反序列化形成了深拷贝,于单例模式初衷违背
4.单例模式没有考虑对象销毁,对于存在垃圾回收的平台不需要考虑,一般不会让类很大。所以消耗很小
5.不能应对多线程环境:在多线程环境下,使用Singleton模式仍有可能得到Singleton类的多个实例对象。
多线程Singleton模式
public class Singleton { private static volatile Singleton Instance = ; private static object lockHelper = new Object(); private Singleton() {} public static Singleton Instance { get { if(instance == null) { lock(lockHelper) { if(instance == null) { instance = new Singleton(); } } } return instance; } } }
双检查(Double Check):就是为了防止多线程的实例创建。
编译器代码编译的时候,会进行代码顺序微调,加了volatile保证代码编译不调整指令。
class Singleton { public static readonly Singleton Instance = new Singleton(); private Singleton() {} }
与
class Singleton { public static readonly Singleton Instance; static Singleton() { Instance = new Singleton(); } private Singleton(); }
的效果是一样的。
静态构造器的角色:
1.静态构造器的执行时间:只在静态字段初始化之前初始化。(内敛初始化会把初始化放到静态构造器中初始化。)
beforefieldinit
2.dot net 机制保证了静态构造器确保了只有一个执行静态构造器。不会有多个静态构造器执行。
3.不支持参数的构造器。
使用.Net类型初始化机制实现多线程Singleton模式
public class Singleton { private static Singleton instance; private Singleton(int x, int y) { this.x = x; this.y = y; } public static Singleton GetInstance(int x, int y) { if (instance == null) { instance = new Singleton(x, y); } else { instance.x = x; instance.y = y; } return instance; } }
Singleton模式扩展
1.将一个实例扩展到n个实例,例如对象池的实现。(其实就是控制构造的过程,Singleton就是控制对象的个数)
2.将new构造器的调用转移到其他类中,例如多个协同工作环境中,某个局部环境只需要拥有某个累的一个实例
3.理解Singleton模式的核心是“如何控制用户使用new对一个类的实例构造器的任意调用。”