单例

饥饿模式:直接初始化,性能问题,如果对象很大,没有使用之前就加载到内存是一种很大的浪费

public final class EagerSingleton   
•  {   
•      private static EagerSingleton singObj = new EagerSingleton();  
•     
•      private EagerSingleton(){   
•      }   
•     
•      public static EagerSingleton getSingleInstance(){   
•         return singObj;
•      }   
•  } 

懒汉模式(延迟加载):不可用。

保证了没有使用之前不会加载;但是线程不安全,可能会多线程同时进行初始化。

public final class LazySingleton   
•  {   
•      private static LazySingleton singObj =null;  
•     
•      private LazySingleton(){   
•      }   
•     
•      public static LazySingleton getSingleInstance(){   
•          if(null == singObj ) singObj = new LazySingleton(); 
•            return singObj;
•      }   
•  }

在初始化方法前面加线程同步Synchronized:不推荐使用。

代价是同步的大家必然会一定程度的降低并发度,影响效率,

public final class ThreadSafeSingleton   
•  {   
•      private static ThreadSafeSingleton singObj = null;  
•     
•      private ThreadSafeSingleton(){   
•      }   
•     
•      public static synchronized ThreadSafeSingleton getSingleInstance(){   
•          if(null == singObj ) singObj = new ThreadSafeSingleton(); 
•              return singObj;
•      }   
•  }

双重检查锁(降低同步的粒度,只在初始化对象时候进行进行同步):这其实一种反面模式,不推荐使用。

假设线程A执行到了第十九行,判断对象为空,于是线程A执行到第二十二行初始化这个对象,但是初始化是需要耗费时间的,但是这个对象的地址已经存在了。
此时线程B也执行到第十九行,他判断不为空,于是直接跳到第二十六行获取这个对象,但是,这个对象还没有被完整的初始化!获取了一个没有初始化完全的对象,这时就出问题了。

public final class DoubleCheckedSingleton   
•  {   
•      private static DoubleCheckedSingletonsingObj = null;  
•     
•      private DoubleCheckedSingleton(){   
•      }   
•     
•      public static DoubleCheckedSingleton getSingleInstance(){   
•          if(null == singObj ) { 
•                synchronized(DoubleCheckedSingleton.class){
•                       if(null == singObj)
•                             singObj = new DoubleCheckedSingleton();
•                }
•           } 
•         return singObj;
•      }   
•  }

静态内部类,和饿汉式机制类似,但又有懒加载的作用。静态内部类在类被装在时并不会立即实例化,而是在需要实例化时,也即是调用getInstance()方法时,才会装载,从而完成实例化。

优先使用这种,类的静态属性只会在第一次加载类的时候初始化,所以在这里,JVM帮助我们保证了线程的安全性,在类进行初始化时,别的线程是无法进入的。

public class _6StaticInnerClassSingleton {

    private static class SingletonInstance{
        private static final _6StaticInnerClassSingleton INSTANCE = new _6StaticInnerClassSingleton();
    }

    private _6StaticInnerClassSingleton(){}

    public static _6StaticInnerClassSingleton getInstance(){
        return SingletonInstance.INSTANCE;
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 10
    评论
评论 10
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

木子松的猫

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值