zoukankan      html  css  js  c++  java
  • 单例模式

    单例模式


    核心实现

    1、构造方法私有化,使其不能在类外部通过new方法实例化该类;

    2、定义一个private static的实例化对象;

    3、定义一个静态方法用于返回该唯一对象;

    饿汉模式(立即加载)

    使用类的时候就已经将对象创建完毕,没有多线程同步的问题,但是会持续占着内存;

    public class Singleton{
        // 将自身实例化对象设置为一个属性,并且static、final修饰
        private static final Singleton instance = new Singleton();
        // 构造方法私有化
        private Singleton(){}
        // 静态方法返回该实例
        public static Singleton getInstance(){
            return instance;
        }
    }
    

    懒汉模式(延迟加载)

    调用get方法的时候才会创建对象,在多线程环境中,完全不能保证单例的状态;

    public class Singleton{
        // 将自身实例化对象设置为一个属性,并用static修饰
        private static Singleton instance;
        // 构造方法私有化
        private Singleotn(){}
        // 静态方法返回该实例
        public static Singleton getInstance(){
            if(instance == null){
                instance = new Singleton();
            }
            return instance;
        }
    }
    

    线程安全的懒汉模式

    在多线程情况下保证了线程安全,但是synchronized效率很低

    public class Singleton{
        // 将自身实例化对象设置为一个属性,并用static修饰
        private static Singleton instance;
        // 构造方法私有化
        private Singleton(){}
        // 静态方法返回该实例,加synchronized关键字实现同步
        public static synchronized Singleton getInstance(){
            if(instance == null){
                instance = new Singleton(); 
            }
            return instance;
        }
    }
    

    双端检索机制

    DCL (Double check lock)也不一定安全,可能存在指令重排序;

    多线程模式的单例模式

    public class SingletonDemo{
        // 加了volatile才是安全的
         private static volatile SingletonDemo instance = null;
         private SingletonDemo(){
             
         }
         // 双端检索机制
         public static singletonDemo getInstance(){
             // 线程2进来时,如果没有使用volatile修饰,可能线程1的a操作的1、3部分已经执行,instance不为null,但是没有具体引用;
             if(instance == null){
                synchronized(SingletonDemo.class){
                     if(instance == null){
                         // 这个new操作具体还有三步
                         // 1. 分配对象内存空间
                         // 2. 初始化对象
                         // 3. 设置instance指向的内存地址;
                         instance = new SingletonDemo(); // a操作
                    }
                }
            }
             return instance;
        }
     }
    
  • 相关阅读:
    Zookeeper ZAB 协议分析
    Docker技术快速精通指南
    Oracle闪回技术详解
    怎样打造一个分布式数据库
    使用js冒泡实现点击空白处关闭弹窗
    也谈谈我对Docker的简单理解
    Docker技术快速精通指南
    Oracle优化网上常见的5个错误观点
    使用Spring AOP实现MySQL读写分离
    RESTEASY ,从学会使用到了解原理。
  • 原文地址:https://www.cnblogs.com/ngrzr/p/15256735.html
Copyright © 2011-2022 走看看