JAVA的单例模式与延时加载

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了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修饰以确保外部类不能访问。

 

 

 

 






































以上是关于JAVA的单例模式与延时加载的主要内容,如果未能解决你的问题,请参考以下文章

《java大法好》之 单例模式

如何实现单例模式

多类加载器的单例模式

14-java的单例设计模式详解

Java中的单例模式

Java设计模式之单例模式