单例模式

定义:确保一个类只有一个实例,并提供全局的访问。

例子:项目里数据库访问类。这个类需要全局访问,而且需要使用反射实例化。因为反射很费资源,所以要求只实例化一个实例。这时候使用单例模式正好解决这个问题。

别人写的简单实现的例子

    /// <summary>
    /// 单例模式的实现
    /// </summary>
    public class Singleton
    {
        // 定义一个静态变量来保存类的实例
        private static Singleton uniqueInstance;

        // 定义私有构造函数,使外界不能创建该类实例
        private Singleton()
        {
        }

        /// <summary>
        /// 定义公有方法提供一个全局访问点,同时你也可以定义公有属性来提供全局访问点
        /// </summary>
        /// <returns></returns>
        public static Singleton GetInstance()
        {
            // 如果类的实例不存在则创建,否则直接返回
            if (uniqueInstance == null)
            {
                uniqueInstance = new Singleton();
            }
            return uniqueInstance;
        }
    }

当多线程访问的时候,多个线程同时建立实例的时候,因为没有建立过实例,多个线程都会去建立线程。

/// <summary>
    /// 单例模式的实现
    /// </summary>
    public class Singleton
    {
        // 定义一个静态变量来保存类的实例
        private static Singleton uniqueInstance;
        //定义锁
        private static readonly object locker=new object();
        // 定义私有构造函数,使外界不能创建该类实例
        private Singleton()
        {
        }

        /// <summary>
        /// 定义公有方法提供一个全局访问点,同时你也可以定义公有属性来提供全局访问点
        /// </summary>
        /// <returns></returns>
        public static Singleton GetInstance()
        {
//当第一个线程访问的时候加锁。
//当第二个线程访问的时候,就要等待第一个对象解锁才能访问
//lock执行完毕,既第一个对象执行完毕解锁。
lock(locker){ // 如果类的实例不存在则创建,否则直接返回 if (uniqueInstance == null) { uniqueInstance = new Singleton(); } } return uniqueInstance; } }

这样执行,会一直加锁和解锁,很浪费性能。应该避免。

/// <summary>
    /// 单例模式的实现
    /// </summary>
    public class Singleton
    {
        // 定义一个静态变量来保存类的实例
        private static Singleton uniqueInstance;
        //定义锁
        private static readonly object locker=new object();
        // 定义私有构造函数,使外界不能创建该类实例
        private Singleton()
        {
        }

        /// <summary>
        /// 定义公有方法提供一个全局访问点,同时你也可以定义公有属性来提供全局访问点
        /// </summary>
        /// <returns></returns>
        public static Singleton GetInstance()
        {
         //当第一个线程访问的时候加锁。
         //当第二个线程访问的时候,就要等待第一个对象解锁才能访问
         //lock执行完毕,既第一个对象执行完毕解锁。
         //(双向锁定)当对象为空的时候,执行加锁。
          if(uniqueInstance == null){
           lock(locker){
            // 如果类的实例不存在则创建,否则直接返回
            if (uniqueInstance == null)
            {
                uniqueInstance = new Singleton();
            }
            }
            }
            return uniqueInstance;
        }
    }
原文地址:https://www.cnblogs.com/Blogs-Wang/p/6400943.html