• JAVA的单例模式与延时加载


    延迟加载(lazy load)是(也称为懒加载),也叫延迟实例化,延迟初始化等,主要表达的思想就是:把对象的创建延迟到使用的时候创建,而不是对象实例化的时候创建。延迟加载机制是为了避免一些无谓的性能开销而提出来的,这种方式避免了性能的浪费。所谓延迟加载就是当在真正需要数据的时候,才真正执行数据加载操作。可以简单理解为,只有在使用的时候,才会发出sql语句进行查询。

    所谓延时加载技术,就是优化内存资源的利用效率,你要用什么,在用的时候再给你,而不是你迟点会用到的时候就马上给你。

    当创建一个对象的子对象开销比较大时,而且有可能在程序中用不到这个子对象,那么就可以考虑用延迟加载的方式来创建子对象。另外就是当一个程序启动时,需要创建多个对象,但仅有几个对象需要立即使用,那么可以将一些不必要的初始化工作延迟到使用的时候。这样可以提高程序的启动速度。

     

     

     

     

    实例一:

    public Class Singleton

    {

    private static Singleton instance;

    private Singleton(){ } //私有无参构造

     

    public static Singleton getInstance(){

    If(instance==null){

    Instance=new Singleton();

    }

    Return instance;

    }

    }

    构造函数私有,方法静态。

    问题:无法保证线程安全,当有多个线程同时访问getInstance的时候,此时若对象为空,就会出现会多个线程同时产生多个Singleton对象。

    此时我们可以修改一下上面的代码,如实例二

     

    实例二:

    publicclass Singleton
    {
    privatestatic Singleton instance;
    privatestaticobject _lock=newobject();

    private Singleton()
    {

    }

    publicstatic Singleton GetInstance()
    {
    if(instance==null)
    {
    lock(_lock)
    {
    if(instance==null)
    {
    instance=new Singleton();
    }
    }
    }
    return instance;
    }
    }

    上述代码使用了双重锁方式较好地解决了多线程下的单例模式实现。先看内层的if语句块,使用这个语句块时,先进行加锁操作,保证只有一个线程可以访问该语句块,进而保证只创建了一个实例。再看外层的if语句块,这使得每个线程欲获取实例时不必每次都得加锁,因为只有实例为空时(即需要创建一个实例),才需加锁创建,若果已存在一个实例,就直接返回该实例,节省了性能开销。

     

    实例三:

    public class Singleton
    {
    private static Singleton instance = new Singleton();
    private Singleton() { }

    public static Singleton getInstance()

    {

    return instance;
    }

    }

    这个方法保证了在第一次加载的时候实例被初始化,且保证了线程安全。但是为进一步要求,我们想要在使用的时候才才初始化Singleton对象,及延迟加载。那么可以使用实例四方法。

     

    实例四:

    public class Singleton {
        private Singleton() { };

       private static class SingletonHolder {
           static Singleton instance = new Singleton();
      }

    public static Singleton getInstance() {
           return SingletonHolder.instance;
       }
       public static void main(String [] args){
          Singleton.getInstance();
       }
    }

    该方法中Singleton有一个静态内部类SingletonHolder,内部类在外部加载的时候并不会加载,在有在调用getInstance才回加载。另外SingletonHolder类使用Private修饰以确保外部类不能访问。

     

     

     

  • 相关阅读:
    MT【90】图论基础知识及相关例题
    MT【89】三棱锥的体积公式
    Qt之界面实现技巧
    QCompleter自动补全
    Qt之开机自启动
    Qt之日志输出文件
    相遇Qt5
    QT中的pro文件的编写
    qt下的跨目录多工程编译
    用QT打开网页
  • 原文地址:https://www.cnblogs.com/zwjcom/p/6092194.html
Copyright © 2020-2023  润新知