美文网首页
单例模式的几种实现方式总结

单例模式的几种实现方式总结

作者: RenHaiRenWjc | 来源:发表于2018-03-25 10:18 被阅读20次

    单例模式

    1. 是什么?
      确保某一个类只有一个实例,而且自行实例化并向整个系统提供这个实例。

    2. 使用场景?
      如访问IO和数据库等资源,创建一个对象需要消耗的资源过多,适合使用单例模式,确保某个类有且只有一个对象。

    3. 关键点
      a. 构造函数不对外开放,一般为 Private
      b. 通过一个静态方法返回单例类对象
      c.确保单例类的对象有且仅只有一个,尤其是在多线程环境下(线程安全)
      d.确保单例类对象在反序列时不会重新构造对象

    4. 示例

    a. 饿汉单例模式
    a0:static变量只会在类装载的时候初始化一次,并且多个实例共享内存区域,非常符合单例的需求
    a1:重点就在于饿,一饿就急就会急着用,没有访问也创建对象

    public class MyClass {
        private static final MyClass mMyClass = new MyClass();
    
        private MyClass() { }
        public static MyClass getMyClass(){
            return mMyClass;
        }
    }
    

    b. 懒汉模式
    b0:只有在使用时才会被实例化
    b1:每次调用 getInstance都进行同步,造成不必要的同步开销,一般不建议用

    public class MyClass {
        private static MyClass instance;
    
        private MyClass(){}
        public static synchronized MyClass getInstance(){
            if (instance==null){
                instance=new MyClass();
            }
            return instance;
        }
    }
    
    

    c. Double Check Lock(DCL)实现单例
    c0:能够在需要时才初始化单例,又能够保证线程安全,且单例对象初始化后调用 getInstance 不进行同步锁,资源利用率高,效率高。
    c1:第一次加载有点稍慢;由于Java内存模型的原因偶尔失败。
    使用最多的单例实现方式

    public class MyClass {
        private static MyClass instance = null;
    
        private MyClass() {}
        public static MyClass getInstance() {
            if (instance == null) {
                synchronized (MyClass.class) {
                    if (instance == null) {
                        instance = new MyClass();
                    }
                }
            }
            return instance;
        }
    }
    
    

    d. 静态内部类单例模式
    第一次调用 getInstance 才会导致虚拟机加载SingletonHolder类,这不仅能确保线程安全,而且能够保证单例对象的唯一性,同时也是延迟了单例的实例化。
    推荐使用

    public class MyClass {
        private MyClass() {}
    
        public static MyClass getInstance() {
            return SingletonHolder.sInstance;
        }
    
        private static class SingletonHolder {
            private static final MyClass sInstance = new MyClass();
        }
    }
    
    

    e.枚举单例
    默认的枚举实例的创建时线程安全的,并且在任何一种情况都是单例
    以上几种单例实现,在反序列化时,会出现重新创建对象的情况。

    public enum SingletonEnum {
        INSTANCE;
        public void doSomething(){
            
        }
    }
    
    

    (完)

    相关文章

      网友评论

          本文标题:单例模式的几种实现方式总结

          本文链接:https://www.haomeiwen.com/subject/nfdhcftx.html