前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >面试最常问的设计模式(一)单例模式/工厂模式/代理模式

面试最常问的设计模式(一)单例模式/工厂模式/代理模式

作者头像
鳄鱼儿
发布2024-05-22 09:02:17
1030
发布2024-05-22 09:02:17
举报

持续创作,加速成长!这是我参与「掘金日新计划 · 10 月更文挑战」的第16天,点击查看活动详情

分类

设计模式分为:创建型模式、结构型模型、行为模型

  • 创建型模式:用于创建对象的设计模式。一般可以简化用户创建对象的过程。其次可以降低耦合度,用户不需要关心对象具体的创建过程。
    • 单例模式⭐️、原型模型、抽象工厂模式、建造者模式、工厂方法模式⭐️
  • 结构型模型:组织对象之间的结构,使其易于扩展。
    • 代理模式⭐️、适配器模式⭐️、桥接模式、装饰器模式、外观模式、享元模式、组合模式
  • 行为模型:主要用于决定对象如何做出行为。
    • 模板方法模式⭐️、策略模式、命令模式、责任链、状态模式、观察者模式⭐️、中介者模式、迭代器模式、访问者模式、备忘录模式、解释器模式

六大原则

  • 开放封闭原则:尽量通过扩展软件实体来解决需求变化,而不是通过修改已有的代码来完成变化。即对扩展开放,对修改封闭,每个类都有自己负责的职责。
  • 里氏替换原则(Liskov Substitution Principle):子类可以扩展父类的功能,但不能改变原有父类的功能,不能破坏继承关系的体系。
  • 依赖倒置原则(Dependence Inversion Principle):面向接口编程,要求在编码中传递参数时,尽量引用高层次的抽象层类。
  • 接口隔离原则(interface segregation principle):使用多个隔离的接口,比使用单个接口要好,降低耦合。
  • 迪米特法则(最少知道原则)(Demeter Principle):一个类对于其他类知道的越少越好,尽量降低类之间的耦合。应该尽量减少对象之间的交互,如果两个对象不必直接通信,那么这两个对象就不应该发生任何直接的相互作用,如果其中一个对象需要调用另外一个对象的某个方法时,可以通过第三者转发这个调用,就是通过引入一个合理的第三者来降低先有对象之间的耦合度,比如引入MQ消息中间件。
  • 单一职责原则(Principle of single responsibility):一个方法/一个类只负责一件职责,各个职责的程序代码改动,不影响其他程序。降低类之间的耦合,提高可维护性和可扩展性。

单例模式⭐️

单例模式需要保证一个类只有一个实例,并提供一个全局访问的方法调用这个实例。

单例模式提供了两种方式,懒汉模式和饿汉模式

  • 懒汉模式:首次使用单例实例的时候创建,之后使用时再判断单例实例是否已创建,如果没有则创建实例。在多线程使用中,需要考虑线程安全问题。
  • 饿汉模式:在该类初始化的时候就创建实例对象,线程是安全的。
代码语言:javascript
复制
/**
 * 懒汉模式:首次使用单例实例的时候创建,之后使用时再判断单例实例是否已创建,如果没有则创建实例。
 */
class LazySingleton {
    private static LazySingleton instance = null;

    private Singleton() {
    }

    // 饿汉模式需要考虑线程安全问题,因为在使用时创建实例,可能有多个线程同时在调用。以下几种实现
    // 1.效率最高,线程安全
    public static LazySingleton getInstance() {
        // 如果对象为空才进入同步方法块,否则返回实例对象
        if (instance == null) {
            synchronized (LazySingleton.class) {
                // 确保线程安全
                if (instance == null)
                    instance = new LazySingleton();
            }
        }
        return instance;
    }

    // 2.静态synchronized方法 线程安全
    public static synchronized LazySingleton getInstance2() {
        if (instance == null)
            instance = new LazySingleton();
        return instance;
    }

    // 3.synchronized class同步块(每次调用都进入同步块) 线程安全
    public static LazySingleton getInstance3() {
        synchronized (LazySingleton.class) {
            if (instance == null)
                instance = new LazySingleton();
        }
        return instance;
    }

    // 4.不加同步锁 线程不安全
    public static LazySingleton getInstance4() {
        if (instance == null)
            instance = new LazySingleton();
        return instance;
    }


}

/**
 * 饿汉模式:在该类初始化的时候就创建实例对象,线程是安全的。
 */
class HungrySingleton {
    // 不管有没有需求,类初始的时候就创建实例对象
    private static final HungrySingleton instance = new HungrySingleton();

    private Singleton() {
    }

    public static final HungrySingleton getInstance() {
        return instance;
    }
}

注意:

  1. 单例模式中,不能使用反射模式创建单例,反射会创建一个新的实例对象。
  2. 懒汉模式,需要考虑线程安全问题。
  3. 单例模式中,构造方法时私有的,不能被继承。

工厂模式

工厂模式中由工厂提供创建对象的接口来代替new创建对象实例,实现调用者与创建者的分离,降低程序耦合。工厂模式又分为简单工厂模式、工厂方法模式和抽象工厂模式。

简单工厂模式

简单工厂模式相当于现实中的一个工厂,我们可以通过工厂生产产品,这里是通过工厂创建对象实例。用户只需要知道对象的名称,工厂就可以返回对应名称的对象实例。

工厂方法模式

在简单工厂模式中,存在这样一个缺点,如果需要增加工厂的产品,那么就需要修改工厂类方法,一个工厂生产多种产品。工厂方法模式就是一个工厂只生产一种产品,后期扩展产品需要创建新工厂。

抽象工厂模式

就工厂模式而言,一个工厂只能生产一种产品,如果要求一个工厂同时兼生产多种产品,这种需求就不能满足。

在抽象工厂模式中,抽象工厂类中定义了多种产品,即定义其子类应该生产哪几种产品。但后期抽象工厂再增加产品时,需要对所有具体工厂进行修改。

区别

  • 简单工厂:所有的产品都由一个工厂生产。如果后期需要增加产品,就需要修改工厂代码。
  • 工厂方法:可以有多个工厂,但一个工厂只生产一种产品。如果后期需要增加产品,那就需要增加工厂类。
  • 抽象工厂:可以有多个工厂,每个工厂可以生产多类产品。如果后期需要增加产品,那么就需要在抽象工厂里加抽象方法,然后修改所有的子类。

代理模式

通过代理控制对象的访问,可以在这个对象调用方法之前、调用方法之后去处理/添加新的功能。

在Spring AOP中,就是应用了代理模式。代理模式实现方法,通常有静态代理和动态代理两种方式。

  • 静态代理:在程序运行前就已经存在代理类,可以是开发者自己便携的代理类或AspectJ等工具生成的代理类。
  • 动态代理:在程序运行时,利用 JDK 的反射机制,动态地在内存中构建代理对象。如Spring AOP
本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2024-05-21,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 分类
  • 六大原则
  • 单例模式⭐️
  • 工厂模式
    • 简单工厂模式
      • 工厂方法模式
        • 抽象工厂模式
          • 区别
          • 代理模式
          相关产品与服务
          消息队列 TDMQ
          消息队列 TDMQ (Tencent Distributed Message Queue)是腾讯基于 Apache Pulsar 自研的一个云原生消息中间件系列,其中包含兼容Pulsar、RabbitMQ、RocketMQ 等协议的消息队列子产品,得益于其底层计算与存储分离的架构,TDMQ 具备良好的弹性伸缩以及故障恢复能力。
          领券
          问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档