• 跟我一起学23种经典设计模式——单例模式


             让我们一起开启设计模式吧!笔者以后会不定时更新我学习设计模式的随笔,一些重要的要点我都直接写在代码的注释里,好了,废话不多说,让我们从单例模式开始吧!

    一、单线程下实例唯一

    namespace SingletonPattern
    {
        /// <summary>
        /// 这种的单例模式只能保证在单线程内实例唯一
        /// </summary>
        public class SingletonOnlyInOneThread
        {
            private static SingletonOnlyInOneThread _instance;
            private SingletonOnlyInOneThread() { }
            public static SingletonOnlyInOneThread Instance//这里作为一个属性来获取
            {
                get
                {
                    if (_instance == null)
                    {
                        _instance = new SingletonOnlyInOneThread();
                    }
                    return _instance;
                }
            }
        }
    }

    二、多线程下实例唯一

    namespace SingletonPattern
    {
        /// <summary>
        /// 在多线程内保证实例唯一
        /// </summary>
        public class SingletonInMultiThread
        {
            private static volatile SingletonInMultiThread _instance;//volatile关键字保证实例在多个线程中同步,即在一个线程内对象内部发生了变化,其它线程内的对象也发生相应的变化
            private static object objectHelper = new object();//帮助对象,用于lock语句
            private SingletonInMultiThread() { }
            public SingletonInMultiThread Instance
            {
                get
                {
                    if(_instance ==null)
                    {
                        lock (objectHelper )//lock关键字使得同一时间内只能有一个线程进入语句块,其它线程必须等待
                        {
                            if (_instance == null)//这里使用的double check来确保在进入lock语句块后还未实例化对象
                            {
                                _instance = new SingletonInMultiThread();
                            }
                        }
                    }
                    return _instance;
                }
            }
        }
    }

    三、实现多线程下实例唯一的简单方式

    namespace SingletonPattern
    {
        /// <summary>
        ///保证实例在多线程内唯一的一种简单实现方式 
        /// </summary>
        public sealed class SingletonInMultiThreadWithEasyWay
        {
            public static readonly SingletonInMultiThreadWithEasyWay Instance = new SingletonInMultiThreadWithEasyWay();
            private SingletonInMultiThreadWithEasyWay() { }
        }
    }

    用reflector反编译后变成:
    public sealed class SingletonInMultiThreadWithEasyWayCompile
        {
            public static readonly SingletonInMultiThreadWithEasyWayCompile Instance;
            static SingletonInMultiThreadWithEasyWayCompile ()//一个静态的构造函数
            {
                Instance = new SingletonInMultiThreadWithEasyWayCompile();
            }
            private SingletonInMultiThreadWithEasyWayCompile() { }
        }
    这样的实现可以自动帮我们加锁实现多线程实例唯一,
    但如果我们如果以这种实现的话,这样会带来的一个问题就是无法实现有参构造函数的单例,因为静态构造函数不允许带参数,解决方法:使用属性或方法在得到实例后进行初始化对象,比如:
    public sealed class SingletonInMultiThreadWithEasyWayCompile
        {
            public static readonly SingletonInMultiThreadWithEasyWayCompile Instance;
            static SingletonInMultiThreadWithEasyWayCompile ()//一个静态的构造函数
            {
                Instance = new SingletonInMultiThreadWithEasyWayCompile();
            }
            private SingletonInMultiThreadWithEasyWayCompile() { }
            public int Property1 { get; set; }
            public int Property2 { get; set; }
            public void Init(int property1, int property2)
            {
                this.Property1 = property1;
                this.Property2 = property2;
            }
        }
  • 相关阅读:
    选择排序与冒泡排序
    判断是否为偶数
    mysql基础之mysql双主(主主)架构
    mysql基础之mysql主从架构半同步复制
    mysql基础之mysql主从架构
    mysql基础之数据库备份和恢复实操
    mysql基础之数据库备份和恢复的基础知识
    mysql基础之日志管理(查询日志、慢查询日志、错误日志、二进制日志、中继日志、事务日志)
    mysql基础之查询缓存、存储引擎
    mysql基础之数据库变量(参数)管理
  • 原文地址:https://www.cnblogs.com/luoweihui/p/3271326.html
Copyright © 2020-2023  润新知