• 常见的几种单例模式


    今天面试官问到单例模式有哪几种,

    我一下子愣了,虽然简单看过单例模式,但是还真不清楚的了解到它还有哪些类型。

    今天决定学习一下。

    单例模式是一种常用的软件设计模式,在它的核心结构中值包含一个被称为单例的特殊类。一个类只有一个实例,即一个类只有一个对象实例。为了减少重复创建实例造成内存浪费。应用的场景如:每台计算机可以有若干个通信端口,系统应当集中管理这些通信端口,以避免一个通信端口被两个请求同时调用。

    单例模式可以分为懒汉式和饿汉式

        懒汉式单例模式:在类加载时不初始化。

        饿汉式单例模式:在类加载时就完成了初始化,所以类加载比较慢,但获取对象的速度快。

    懒汉式单例:

    /**
     * 这个是懒汉模式,并且线程非安全
     */
    public class SingletonDemo1 {
    
        private static SingletonDemo1 instance;
    
        private SingletonDemo1() {
    
        }
    
        public static SingletonDemo1 getInstance() {
            // 若当前实例为空,重新创建内存指向一个新的实例
            if (instance == null) {
                instance = new SingletonDemo1();
    
            }
            return instance;
        }
    }

    上面那个懒汉模式有个问题就是线程不安全:因此可以加上 synchronized 关键字保证线程安全

    /**
     * 这个是懒汉模式,线程安全的
     */
    public class SingletonDemo2 {
    
        private static SingletonDemo2 instance;
    
        private SingletonDemo2() {
    
        }
    
        // 加上 synchronized 保证创建线程线程安全
        public static synchronized SingletonDemo2 getInstance() {
            // 若当前实例为空,重新指向一个新的实例
            if (instance == null) {
                instance = new SingletonDemo2();
    
            }
            return instance;
        }
    }

    接下来是饿汉模式,字面意思理解起来就是饥渴的,迫切需要的,即类加载时就要初始化

    /**
     * 这个是饿汉模式,类一加载就要初始化
     */
    public class SingletonDemo3 {
    
        // 在成员变量声明的时候就要初始化
        private static SingletonDemo3 instance = new SingletonDemo3();
    
        private SingletonDemo3() {
    
        }
    
    
        public static SingletonDemo3 getInstance() {
            // 若当前实例为空,重新指向一个新的实例
            if (instance == null) {
                instance = new SingletonDemo3();
    
            }
            return instance;
        }
    }

    接下来, 静态内部类这种方式同样利用了classloder的机制来保证初始化instance时只有一个线程,它跟前几种方式不同的是:Singleton类被装载了,instance不一定被初始化。因为SingletonHolder类没有被主动使用,只有显示通过调用getInstance方法时,才会显示装载SingletonHolder类,从而实例化instance。想象一下,如果实例化instance很消耗资源,我想让他延迟加载,另外一方面,我不希望在Singleton类加载时就实例化,因为我不能确保Singleton类还可能在其他的地方被主动使用从而被加载,那么这个时候实例化instance显然是不合适的。这个时候,这种方式相比饿汉方法就显得更合理。

    /**
     * 这个是懒汉模式变种,使用静态内部类创建
     */
    public class SingletonDemo4 {
    
        private static class SingletonHolder{
            private static final SingletonDemo4 instance = new SingletonDemo4();
        }
    
        private SingletonDemo4() {
    
        }
    
    
        public static SingletonDemo4 getInstance() {
            // 调用内部类的属性创建新的实例
            return SingletonHolder.instance;
        }
    }
  • 相关阅读:
    “用户、组或角色'XXX'在当前数据库中已存在”问题
    C#与Java在继承静态类上的区别
    Java中静态内部类的理解
    python第三天
    python第二天
    python第一天
    applicationhost.config web.config
    IIS:错误: 无法提交配置更改,因为文件已在磁盘上更改
    SMO 的环境
    从客户端中检测到有潜在危险的 Request.Form 值
  • 原文地址:https://www.cnblogs.com/libera11/p/9174014.html
Copyright © 2020-2023  润新知