单例模式解析

       常用单例模式解析

单例模式是一种比较常用且简单的设计模式,单例模式限制了待创建的对象在内存中有且仅有一个。

一.非线程安全的单例模式

public classSingleton{
      public static Singletion instance;
      private Singleton(){
}
public Singletion getInstance(){
  if(instance==null){   //(1)
       instance =newSingleton();(2)
  }
  return instance;
}
}

1.单例模式代码特点概述:该单例模式instance必须是static的,getInstance是静态的方法,构造函数必须设置为私有函数

2.多线程环境分析:假设存在两个线程:线程1和线程2,假如线程1和线程2同时访问Singleton.getInstance()方法,此时假设线程1先执行步骤(1),进入if内部,进行对象的创建工作(对象的创建通常分为两部,第一步在java堆中分配对象所需要的内存,第二步将内存地址分配给instance),与此同时线程2也执行步骤(1),但是线程1尚未执行到创建对象的第二步,此时instance==null,所以线程2同样进入了if语句的内部,再次创建了一个Singleton对象。

该单例模式姑且称其为模式1,该模式在单线程的环境下可以实现单例,但是在多线程的环境下无法实现单例。

二.适用于多线程环境下的单例模式

public classSingleton{
      public static Singleton instance;
      private Singleton(){
      }
      public static Singleton getInstance(){
      synchronized(Singleton.class){//(0)
          if(instance==null){//(1)
              instance=newSingleton();//(2)
           }
      }
      return intance;//(3)
   }
}

1.多线程环境性能分析:该单例模式适用于多线程环境,若存在两个线程同时访问Singleton.getInstance()方法,假定线程1先执行步骤(0),步骤(1),进入if语句内部,synchronize关键字会加一把同步锁,接着线程1顺次执行(1),(2),(3)步骤创建一个对象,同样假设线程1在执行步骤(0),(1),(2)时,线程2进入方法内部,执行到步骤(0),发现同步锁未被释放,线程2此时只能等待,等待线程1执行完(1),(2),(3)释放同步锁后,线程2方能执行步骤(1),最后直接跳转到(3)。完成多线环境下的单例模式的设计。

2.该单例模式可以适应多线程的环境,但是性能表现不好,因为线程每次访问getInstance()时,都会添加一把同步锁,而添加同步锁是非常消耗性能的事情,所应该单例模式的性能表现不佳

三.双重判断的单例模式

public classSingleton{
      public static Singleton instance;
      private Singleton(){
}
      public static Singleton getInstance(){
      if(intance==null){(0)
           synchronized(Singleton.class){//(1)
                 if(instance==null){//(2)
                      instance=newSingleton();//(3)
                      }
                 }
           }
           return instance;//(4)
      }
}

1.多线程环境下的性能分析:该单例子模式相比较于方式二,主要减少了同步锁的添加,从这方面对效率进行优化

2.利用了双重if循环实现了单例模式,实现的代码比较复杂,容易出错。

四.改进的单例模式

public classSingleton{
      public static Singleton instance = newSingleton();
      private Singleton(){
}
      public static Singleton getInstance(){
           return instance;
      }
}

1.该单例模式可以适应线程环境的要求,利用Singleton类只被加载一次的特性,完成instance的创建

2.该单例模式拥有一个缺陷,无论是否使用该对象,一旦Singleton类被加载那么instance就分配了内存,在加载速度和内存的利用情况方面有缺陷

五.静态内部类实现的单例模式

public classSingleton{
      public static class SingletionHolder{
      public static final Singleton instance =new Singleton();}
      private Singleton(){}
      public static Singleton getInstance(){
           return Singleton.instance;//(4)
      }
}

1.该单例模式利用类加载机制来适用于多线程的环境,并且利用了静态内部类只在使用时才加载的特性克服了方法4的缺点,只有在使用到该对象是才会分配内存空间,对内存的利用非常合理。


  • 5
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值