问题:单例模式有什么用处?
有些对象我们只需要一个,比如说线程池,对话框,缓存,网站计数器,任务管理器,打印机,显卡等设备的驱动程序对象。这些对象只能有一个实例,如果制造出多个实例,就会导致许多问题产生,比如程序的异常行为,资源使用过量或者是不一致的结果等等。
解决方法:使用单例模式;
单例模式:确保一个类只有一个实例,并提供一个全局的访问点;
单例模式分类:
饱汉式:
为什么叫饱汉式呢?因为他的实例不是在一开始就创建好的,我们可以看作他是饱的,不着急创建实例,在需要的时候才去创建;
饱汉式优点:
资源利用率高,不执行getInstance()就不会被实例,可以执行该类的其他静态方法;
饱汉式缺点:
线程不安全,第一次加载时不够快,多线程使用不必要的同步开销大;
饿汉式:
饿汉式我们就可以看成他很饿,急着创建实例,在JVM加载这个类的时候就创建好了这个实例;
饿汉式的优点:
1.线程安全 ;
2.在类加载的同时已经创建好一个静态对象,调用时反应速度快;
饿汉式缺点:
可能会浪费资源,如果一直没有调用getInstance方法,但执行该类的其他静态方法或者加载了该类(class.forName),那么这个实例仍然初始化;
饱汉式和饿汉式的区别就是两者创建实例的时间不同,饱汉式在需要的时候才去创建,饿汉式是一开始就创建好;
上面说到了饱汉式线程不安全,我们有没有办法让饱汉式安全呢?答案是肯定的;
方法一:只要把getInstance方法变为同步方法(synchronized)方法就可以避免线程安全的问题;
但是方法一有个问题:同步会降低性能,有没有不降低性能又线程安全的方法,或者说减少同步的次数?这时候就要看方法二了;
方法二:使用“双重检查锁”,在getInstance中减少使用同步;
双重检查锁也存在缺点:第一次加载时反应不快,由于java内存模型一些原因偶尔失败
总结:一般建议采用饿汉式,不建议采用饱汉式;
原文地址:https://www.cnblogs.com/yang457556017/p/9060201.html