博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
单例模式
阅读量:7106 次
发布时间:2019-06-28

本文共 2035 字,大约阅读时间需要 6 分钟。

  hot3.png

//饿汉式单例类.在类初始化时,已经自行实例化.//典型的空间换时间 public class Singleton1 {    private Singleton1() {}    private static final Singleton1 single = new Singleton1();    //静态工厂方法     public static Singleton1 getInstance() {        return single;    }    }

//双重锁定public class Singleton {    private volatile static Singleton instance = null;    private Singleton(){}    public static Singleton getInstance(){        //先检查实例是否存在,如果不存在才进入下面的同步块        if(instance == null){            //同步块,线程安全的创建实例            synchronized (Singleton.class) {                //再次检查实例是否存在,如果不存在才真正的创建实例                if(instance == null){                    instance = new Singleton();                }            }        }        return instance;    }}/*被volatile修饰的变量的值,将不会被本地线程缓存,所有对该变量的读写都是直接操作共享内存,从而确保多个线程能正确的处理该变量。注意:在java1.4及以前版本中,很多JVM对于volatile关键字的实现的问题,会导致“双重检查加锁”的失败,因此“双重检查加锁”机制只只能用在java5及以上的版本。双重校验锁:麻烦,在当前Java内存模型中不一定都管用,某些平台和编译器甚至是错误的,因为instance = new MaYun()这种代码在不同编译器上的行为和实现方式不可预知。*/
//饿汉改进/*    要想很简单地实现线程安全,可以采用静态初始化器的方式,它可以由JVM来保证线程的安全性。比如前面的饿汉式实现方式。但是这样一来,不是会浪费一定的空间吗?因为这种实现方式,会在类装载的时候就初始化对象,不管你需不需要。如果现在有一种方法能够让类装载的时候不去初始化对象,那不就解决问题了?一种可行的方式就是采用类级内部类,在这个类级内部类里面去创建对象实例。这样一来,只要不使用到这个类级内部类,那就不会创建对象实例,从而同时实现延迟加载和线程安全。    当getInstance方法第一次被调用的时候,它第一次读取SingletonHolder.instance,导致SingletonHolder类得到初始化;而这个类在装载并被初始化的时候,会初始化它的静态域,从而创建Singleton的实例,由于是静态的域,因此只会在虚拟机装载类的时候初始化一次,并由虚拟机来保证它的线程安全性。这个模式的优势在于,getInstance方法并没有被同步,并且只是执行一个域的访问,因此延迟初始化并没有增加任何访问成本。*/public class Singleton {    private Singleton(){}    /**     *    类级的内部类,也就是静态的成员式内部类,该内部类的实例与外部类的实例     *    没有绑定关系,而且只有被调用到时才会装载,从而实现了延迟加载。     */    private static class SingletonHolder{        /**         * 静态初始化器,由JVM来保证线程安全         */        private static Singleton instance = new Singleton();    }       public static Singleton getInstance(){        return SingletonHolder.instance;    }}

还有一种选择

  /*枚举实现的Singleton     */    enum TestSingleton3 {      INSTANCE;      public static TestSingleton3 getInstance() {        return INSTANCE;     }  }

转载于:https://my.oschina.net/dadou/blog/490213

你可能感兴趣的文章
vim、gvim在windows下中文乱码的终极解决方式
查看>>
大型企业网络配置系列课程详解(一)---OSPF单区域配置与相关概念的理解
查看>>
Exported activity does not require permission
查看>>
StackOverflow发布年度开发者调查报告:JavaScript备受欢迎
查看>>
自平衡二叉查找树
查看>>
shell脚本中的数据传递方式
查看>>
Shiro系列(0) - 权限管理在J2EE企业级开发中的应用与实战
查看>>
Gdevops峰会归来
查看>>
[20170215]ORA-00088与DG Gap监测与解决4
查看>>
根据输入的日期,控制台打印格式化日历
查看>>
前端性能影响思维导图
查看>>
过滤器控制用户登录
查看>>
MVC3 Razor视图引擎的基础语法
查看>>
CCan's sign in to Appstore - This action could not be completed
查看>>
Linux下安装JDK及其配置环境变量
查看>>
6、Eternal框架-渲染者
查看>>
麻省:第17.18课
查看>>
maven项目打包时去除dependency-reduced-pom.xml文件
查看>>
Win10下Eclipse插件EasyShell兼容问题处理
查看>>
backbone总结
查看>>