23种设计模式-模板方法(Template Method)设计模式

文章目录

  • 一.什么是模板方法模式?
  • 二.模板方法模式的特点
  • 三.模板方法模式的结构
  • 四.模板方法模式的应用场景
  • 五.模板方法模式的优缺点
  • 六.模板方法模式的C++实现
  • 七.模板方法模式的JAVA实现
  • 八.代码解析
  • 九.总结

类图: 模板方法设计模式类图

一.什么是模板方法模式?

模板方法模式(Template Method Pattern)是一种行为型设计模式,它定义了一个操作中的算法骨架,而将一些步骤的实现延迟到子类中。通过这种方式,模板方法允许子类在不改变算法结构的情况下重新定义某些步骤的具体实现。

二.模板方法模式的特点

  1. 算法骨架固定:整体流程在父类中定义,子类只需实现特定步骤。
  2. 代码复用:通用的算法步骤可以在父类中实现,避免重复代码。
  3. 扩展灵活:新增子类时,只需重写相关步骤,无需修改已有代码。

三.模板方法模式的结构

  1. AbstractClass(抽象类)
    • 定义算法的骨架(TemplateMethod),包括一系列步骤(PrimitiveOperation)。
    • 部分步骤由子类实现(抽象方法)。
  2. ConcreteClass(具体类)
    • 实现抽象类定义的抽象方法。
    • 可以根据需要扩展或修改步骤的具体实现。
      模板方法类图

四.模板方法模式的应用场景

  1. 多个子类有共同行为逻辑,但具体实现不同。
  2. 固定的流程需要扩展某些步骤
  3. 避免重复代码,提取通用逻辑。

五.模板方法模式的优缺点

  • 优点
    • 提高代码复用性。
    • 强制遵循一致的算法框架。
    • 易于维护和扩展。
  • 缺点
    • 子类数目较多时,代码可能变得复杂。
    • 设计要求较高,需要仔细分析算法流程。

六.模板方法模式的C++实现

#include <iostream>
using namespace std;// 抽象类 AbstractClass
class AbstractClass {
public:// 模板方法,定义算法骨架void TemplateMethod() {PrimitiveOperation1(); // 第一步PrimitiveOperation2(); // 第二步Hook();                // 钩子方法(可选)}// 基本操作,子类必须实现virtual void PrimitiveOperation1() = 0;virtual void PrimitiveOperation2() = 0;// 钩子方法,子类可以选择性重写virtual void Hook() {cout << "AbstractClass: Default Hook implementation.\n";}virtual ~AbstractClass() = default;
};// 具体类 ConcreteClass
class ConcreteClass : public AbstractClass {
public:void PrimitiveOperation1() override {cout << "ConcreteClass: Implementing PrimitiveOperation1.\n";}void PrimitiveOperation2() override {cout << "ConcreteClass: Implementing PrimitiveOperation2.\n";}void Hook() override {cout << "ConcreteClass: Overriding Hook method.\n";}
};// 客户端代码
int main() {cout << "Using Template Method Pattern:\n";AbstractClass* obj = new ConcreteClass();obj->TemplateMethod(); // 调用模板方法delete obj;return 0;
}

七.模板方法模式的JAVA实现

// 抽象类
abstract class AbstractClass {// 模板方法public final void TemplateMethod() {PrimitiveOperation1();PrimitiveOperation2();}// 抽象基本操作(必须由子类实现)protected abstract void PrimitiveOperation1();protected abstract void PrimitiveOperation2();
}// 具体类A
class ConcreteClassA extends AbstractClass {@Overrideprotected void PrimitiveOperation1() {System.out.println("ConcreteClassA: Performing PrimitiveOperation1");}@Overrideprotected void PrimitiveOperation2() {System.out.println("ConcreteClassA: Performing PrimitiveOperation2");}
}// 具体类B
class ConcreteClassB extends AbstractClass {@Overrideprotected void PrimitiveOperation1() {System.out.println("ConcreteClassB: Performing PrimitiveOperation1");}@Overrideprotected void PrimitiveOperation2() {System.out.println("ConcreteClassB: Performing PrimitiveOperation2");}
}// 客户端代码
public class TemplateMethodPatternDemo {public static void main(String[] args) {// 使用 ConcreteClassAAbstractClass classA = new ConcreteClassA();System.out.println("ConcreteClassA Template Method Execution:");classA.TemplateMethod();// 使用 ConcreteClassBAbstractClass classB = new ConcreteClassB();System.out.println("\nConcreteClassB Template Method Execution:");classB.TemplateMethod();}
}

八.代码解析

  1. 抽象类
    • TemplateMethod() 是模板方法,定义了算法的执行顺序。
    • PrimitiveOperation1 和 PrimitiveOperation2 是抽象方法,具体实现由子类完成。
    • Hook 是钩子方法,提供默认实现,子类可以选择性重写。
  2. 具体类
    • ConcreteClass 实现了抽象类的抽象方法,并可根据需要覆盖钩子方法。
  3. 客户端代码
    • 创建一个具体类的实例,通过抽象类指针调用模板方法。

九.总结

 模板方法模式通过定义一个算法的通用骨架,为子类提供了灵活的扩展点。它适用于多个子类具有相似逻辑但部分实现不同的场景。通过这种模式,代码的复用性和扩展性得到了极大提升,同时保证了算法逻辑的一致性。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/61477.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

MySQL45讲 第二十五讲 高可用性深度剖析:从主备原理到策略选择

文章目录 MySQL45讲 第二十五讲 高可用性深度剖析&#xff1a;从主备原理到策略选择一、MySQL 主备基础原理&#xff08;一&#xff09;主备关系与数据同步&#xff08;二&#xff09;主备切换流程 二、主备延迟分析&#xff08;一&#xff09;主备延迟的定义与计算&#xff08…

VuePress v2 快速搭建属于自己的个人博客网站

目录 为什么用VuePress&#xff1f; 一、前期准备 Node.js 使用主题快速开发 二、VuePress安装 三、个性化定制 修改配置信息 删除不需要的信息 博客上传 四、部署 使用github快速部署 初始化仓库 本地配置 配置github的ssh密钥 部署 为什么用VuePress&#xff…

PostgreSQL常用时间函数与时间计算提取示例说明

文章目录 常用函数与常量to_timestamp(字符串转时间戳、数字转时间戳)date与to_date(字符串转日期、时间戳转日期)interval(时间计算)基本操作与格式混合运算 to_char(各种时间转字符串)extract(提取时间字段&#xff0c;年月日时分秒&#xff0c;周、季度&#xff0c;第几周、…

SlickGrid点击/双击事件

分析 SlickGrid提供了点击事件方法grid.onClick和grid.onDblClick用于捕获用户对表格列的点击&#xff0c;捕获到点击事件之后&#xff0c;修改表格数据&#xff0c;然后使用grid.updateRow方法将修改后的数据更新到表格中。 展示 代码 创建grid&#xff08;HTML&#xff09;…

【Unity ShaderGraph实现流体效果之Node入门(二)】

Unity ShaderGraph实现流体效果之Node入门&#xff08;二&#xff09; 前言Shader Graph NodeStep NodeMultiply NodeRotate About AxisAddfresnel effectIs Front Face 前言 在&#xff08;一&#xff09;中讨论了一部分在制作流体效果时使用的Node&#xff0c;本章继续将剩余…

集合卡尔曼滤波(Ensemble Kalman Filter),用于二维滤波(模拟平面上的目标跟踪),MATLAB代码

集合卡尔曼滤波&#xff08;Ensemble Kalman Filter&#xff09; 文章目录 引言理论基础卡尔曼滤波集合卡尔曼滤波初始化预测步骤更新步骤卡尔曼增益更新集合 MATLAB 实现运行结果3. 应用领域结论 引言 集合卡尔曼滤波&#xff08;Ensemble Kalman Filter, EnKF&#xff09;是…

解决Docker环境变量的配置的通用方法

我们部署的很多服务都是以Docker容器的形式存在的。 在运行Docker容器前&#xff0c;除了设置网络、数据卷之外&#xff0c;还需要设置各种各样的环境变量。 有时候&#xff0c;由于容器版本的问题&#xff0c;一些文档没有及时更新&#xff0c;可能同时存在多个新旧版本的环…

2446.学习周刊-2024年46周

封面 拍摄于11月17日&#xff0c;身心疲惫的时候&#xff0c;去山里走走看看风景&#xff0c;富氧的环境能缓解身心疲劳。 ✍优秀博文 # 深度解析数仓建模与指标体系构建的底层逻辑 | 金字塔原理在数仓建模分析中的应用基于“理采存管用”的数据中台建设方案业务逻辑不要放入…

自然语言处理:第六十三章 阿里Qwen2 2.5系列

本人项目地址大全&#xff1a;Victor94-king/NLP__ManVictor: CSDN of ManVictor 项目地址: QwenLM/Qwen2.5: Qwen2.5 is the large language model series developed by Qwen team, Alibaba Cloud. 官网地址: 你好&#xff0c;Qwen2 | Qwen & Qwen2.5: 基础模型大派对&a…

六、卷积神经网络(CNN)基础

卷积神经网络&#xff08;CNN&#xff09;基础 前言一、CNN概述二、卷积层2.1 卷积2.2 步幅(Stride)2.3 填充(Padding)2.4 多通道卷积2.5 多卷积计算2.6 特征图大小计算2.7 代码演示 三、池化层3.1 池化层计算3.1.1 最大池化层3.1.2 平均池化层 3.2 填充(Padding)3.3 步幅(Stri…

通过vite+vue3+pinia从0到1搭建一个uniapp应用

最近项目上要做一个app&#xff0c;选择了用uniapp作为开发框架&#xff1b;我大概看了一下uniapp的文档&#xff0c;根据文档从0到1搭了一个uniapp应用供大家参考。 因为本人习惯使用了WebStorm编译器&#xff0c;但是uniapp官方推荐使用HBuilder搭建&#xff0c;如果和我一样…

【Pytorch】torch.nn.functional模块中的非线性激活函数

在使用torch.nn.functional模块时&#xff0c;需要导入包&#xff1a; from torch.nn import functional 以下是常见激活函数的介绍以及对应的代码示例&#xff1a; tanh (双曲正切) 输出范围&#xff1a;(-1, 1) 特点&#xff1a;中心对称&#xff0c;适合处理归一化后的数据…

java-贪心算法

1. 霍夫曼编码&#xff08;Huffman Coding&#xff09; 描述&#xff1a; 霍夫曼编码是一种使用变长编码表对数据进行编码的算法&#xff0c;由David A. Huffman在1952年发明。它是一种贪心算法&#xff0c;用于数据压缩。霍夫曼编码通过构建一个二叉树&#xff08;霍夫曼树&a…

【数据结构】【线性表】【练习】反转链表

申明 该题源自力扣题库19&#xff0c;文章内容&#xff08;代码&#xff0c;图表等&#xff09;均原创&#xff0c;侵删&#xff01; 题目 给你单链表的头指针head以及两个整数left和right&#xff0c;其中left<right&#xff0c;请你反转从位置left到right的链表节点&…

实时数仓:Lambda架构和Kappa架构有什么联系和区别

Kappa 和 Lambda 架构是处理大数据和实时数据流的两种不同设计模式。以下是对这两种架构的概述和比较&#xff1a; Lambda 架构 定义&#xff1a; Lambda 架构的全称是 Lambda Architecture。这个架构旨在处理大规模数据&#xff0c;结合了批处理和流处理的优点&#xff0c;以…

vllm源码解析(一):整体架构与推理代码

vlllm官方代码更新频发,每个版本都有极大变动, 很难说哪个版本好用. 第一次阅读vllm源码是0.4.0版本,对这版圈复杂度极高的调度代码印象深刻 0.4.1对调度逻辑进行重构,完全大变样, 读代码速度快赶不上迭代的速度了。 现在已经更新到0.5.4, 经过长时间观察&#xff0c;发现主要的…

数据库index(索引)使用注释事项

1、索引类型&#xff0c;通常选择NORMAL或者UNIQUE. NORMAL&#xff1a;正常的一种索引吧。 UNIQUE:索引列必须是不能重复的。 2、索引方法&#xff1a;通常选择BTREE 3、使用SQL查询的时候&#xff0c;不需要特别处理索引的字段。数据库会自动的处理&#xff0c;提升SQL的查…

集成了高性能ARM Cortex-M0+处理器的一款SimpleLink 2.4 GHz无线模块-RF-BM-2340B1

蓝牙模组 - RF-BM-2340B1是基于美国TI的CC2340R5为核心设计的一款SimpleLink 2.4 GHz 无线模块。支持Bluetooth 5.3 Low Energy、Zigbee 、IEEE 802.15.4g、TI 15.4-Stack (2.4 GHz)及私有协议。集成了高性能ARM Cortex-M0处理器&#xff0c;具有512 KB Flash、32 KB超低泄漏SR…

[QDS]从零开始,写第一个Qt Design Studio到程序调用的项目

前言 最近在使用Qt Design Studio进行开发&#xff0c;但是简中网上要不就是只搜得到Qt Designer(Qt Creator内部库)&#xff0c;要不就只搜得到一点营销号不知道从哪里搬来的账号&#xff0c;鉴于Qt Design Studio是一个这么强大的软件&#xff0c;自然是需要来进行一下小小的…

Spring Boot实现License生成和校验

Spring Boot实现License生成和校验 证书准备 # 1. 生成私钥库 # validity&#xff1a;私钥的有效期&#xff08;天&#xff09; # alias&#xff1a;私钥别称 # keystore&#xff1a;私钥库文件名称&#xff08;生成在当前目录&#xff09; # storepass&#xff1a;私钥库密码…