单例

作者: 小虫虫奇遇记 | 来源:发表于2020-08-13 11:26 被阅读0次
    • 双重锁检测

    public class SingleInstance{
       //volatile:禁止指令重排序;可见性保证
      private static volatile SingleInstance instance  = null;
      private SingleInstance(){ }
      public static SingleInstance getInstance(){
        if(instance == null){      // 性能考虑,细化synchronized同步块粒度
            synchronized(Singleton.class){
                if(instance == null){   // 防止多次初始化
                  instance = new SingleInstance();
                }
            }
          }
    return instance;
    }
    }
    

    new SingleInstance()指令
    1.加载到内存,分配内存地址
    2.执行对象初始化
    3.赋值
    volatile 保证了2->3的顺序

    • 破坏单例

    1. 反射
      Singleton singleton = Singleton.getInstance();
        try {
          Constructor<Singleton> constructor = Singleton.class.getDeclaredConstructor();
          constructor.setAccessible(true);
          Singleton reflectSingleton = constructor.newInstance();
          System.out.println(reflectSingleton == singleton);
        } catch (Exception e) {
          // TODO Auto-generated catch block
          e.printStackTrace();
        }
    

    阻止:
    getInstance中加判断,采用一个全局变量,初始化过就不再初始化。

    1. 继承Clonable接口,重写clone方法
      @Override
      protected Object clone() throws CloneNotSupportedException {
        // TODO Auto-generated method stub
        return super.clone();
      }
    

    破坏:clone方法不调用super.clone() 直接返回instance单例对象
    ⚠️ clone是浅拷贝,也就是说对象的引用对象不会被拷贝。需要深拷贝的话,引用对象也要实现clone方法,该对象引用的其他对象也clone一份

    1. 序列化 implements Serializable
      FileOutputStream.writeObject
      FileInputStream.readObject
      阻止:implements Serializable,重写 readResolve
      protected Object readResolve() throws ObjectStreamException{
        return mInstance;
      }
    

    相关文章

      网友评论

          本文标题:单例

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