代码改变世界

Singleton--单例模式笔记

2010-04-27 15:42  yonger  阅读(249)  评论(1)    收藏  举报

.NET下的单例模式 [单例模式保证两点,1.保证每个类有且只有一个 Singleton  实例,2.客户端通过一个全局的访问点来访问这个实例且自行实例化

     --俺有6个漂亮的老婆,她们的老公都是我,我就是我们家里的老公Singleton,她们只要说道“老公”,都是指的同一个人,那就是我(刚才做了个梦啦,哪有这么好的事) 

         它的主要特点不是根据客户程序调用生成一个新的实例,而是控制某个类型的实例数量——唯一一个

 1. 逻辑模型

   

2.物理模型

   

3.保证线程安全的双重检验锁定

       public class SingLeton

    {

        private volatile static SingLeton _Intance = null;

        protected SingLeton() { }

        public static SingLeton GetIntance(){

            if (_Intance == null)

                lock (typeof(SingLeton))

                    if (_Intance == null)

                        _Intance = new SingLeton();

            return _Intance;

        }注:使用 typeof 操作并添加 volatile 关键字,以确保没有对代码进行优化程序重新排序。

4. 静态初始化,删除惰性初始化简化双重检验锁定示例(达到上例一样的效果)

     public sealed class SingLeton

    {

        public SingLeton() { }

        private static readonly SingLeton intance = new SingLeton();

        public  static  SingLeton Intance

        {return intance;} 

    }

    注意要点:(1)修改为密封类,因为密封类本身是不能继承的。(以禁止派生子类而引发出来歧异)

                  (2)删除了惰性初始化代码,删除了Intance()方法,并对_Intance变量做了大量修改(修改为公共的访问级别和将变量标记为只读,以及声明时初始化该变量)。

                  (3)最初使用惰性初始化的主要原因是要获取仅在第一次调用 Instance() 方法中创建实例的行为,与在.NET框架中首先初始化静态成员等同。任何使用方调用该

                         类的静态成员将被加载和初始化。 

                   (4)是否保证线程安全? .NET框架中保证了静态成员初始化的线程安全。

                   (5)这种方法唯一的潜在缺点是,您对实例化机制的控制权较少 ,在大多数情况下,静态初始化是在 .NET 中实现 Singleton 的首选方法。

 5.Singleton 延迟初始化 (这里用到了嵌套类

     public sealed class Singleton

    {

        Singleton(){ }

        public static Singleton Instance

        {

            get { return Nested.instance; }

        }

        class Nested

        {

            static Nested() { }

            internal static readonly Singleton instance = new Singleton();

        }

    } 注:在这里,含有静态成员的Nested类将触发实例化,这就意味着这个实例化过程是完全延迟。

 6.参数化的Singleton

 7.跨进程的Singleton 

 8.扩展Singleton

 9.工厂辅助Singleton 

 10.使用单例模式需要注意

         (1)不要使用单例模式存取全局变量。这违背了单例模式的用意,最好放到对应类的静态成员中

         (2)不要将数据库连接做成单例,因为一个系统可能会与数据库有多个连接,并且在有连接池的情况下,应当尽可能及时释放连接。Singleton模式由于使用静态成员存储类实例,所以可能会造成资源无法及时释放,带来问题