「聊设计模式」之模板方法模式(Template Method)

2023-09-20 15:56:32

🏆本文收录于《聊设计模式》专栏,专门攻坚指数级提升,助你一臂之力,带你早日登顶🚀,欢迎持续关注&&收藏&&订阅!


前言

  在软件开发中,设计模式是经典的解决方案,它们被广泛应用于面向对象的程序设计中。其中,模板方法模式(Template Method)是一种常用的行为型设计模式,它定义一个操作中的算法骨架,而将一些步骤延迟到子类中实现。本文将从原理、实现以及应用场景三个方面来介绍模板方法模式。

摘要

  模板方法模式是一种基于继承的设计模式,它通过抽象父类定义一系列的抽象方法和模板方法,而由具体的子类来实现这些抽象方法,从而完成对算法的具体实现。模板方法模式遵循“开闭原则”,能够很好地解决代码复用、扩展性和屏蔽细节等问题。

模板方法模式

模式概念

  模板方法模式是一种行为型设计模式,它定义一个算法的骨架,将一些步骤延迟到子类中。模板方法使得子类可以在不改变算法结构的情况下,重新定义算法的某些步骤。它通过将相同的代码抽象到父类中来避免代码重复和复杂性,而通过子类的扩展来实现算法的不同变化。模板方法模式是一种可扩展性很强的模式,因为它使用了多态性和继承来实现不同的算法变化。模板方法模式在软件开发中广泛应用于框架开发、算法设计和复杂业务逻辑的实现。

模式结构

模板方法模式的结构包括以下几个角色:

  1. 抽象类(Abstract Class):定义了一系列抽象方法和模板方法。其中模板方法定义了算法的骨架,而抽象方法则需要子类去实现。

  2. 具体类(Concrete Class):实现了抽象类中定义的抽象方法,完成算法中具体的步骤。同时,它还可以重写模板方法中的某些步骤,来实现算法的变化。

通过这种方式,模板方法模式将算法的具体实现推迟到具体子类中,从而实现了算法的复用和扩展。

如下是模板方法模式的UML类图:

在这里插入图片描述

模式优缺点

优点

1.模板方法模式提供了一种代码复用的方式,将实现相同或类似的方法抽象到父类中,减少了代码的重复性。
2.模板方法模式提供了一种易于维护的方式,由于具体实现都在父类中,所以在需要修改时只需要在父类中修改即可,不需要修改每个子类。
3.模板方法模式提高了代码的灵活性,通过抽象出一些方法,可以方便地扩展子类功能。

缺点

1.在父类中定义了抽象方法,要求子类实现,如果父类的AbstractClass在设计时不够完善,或者需要修改时,会对所有的子类造成影响。
2.模板方法模式降低了程序的灵活性,当父类增加新的抽象方法时,所有子类都必须进行修改,否则编译会出错。

应用场景

模板方法模式适用于以下场景:

  • 在多个类中存在相似的算法,但具体实现不同的情况下,可以使用模板方法模式将算法的公共部分抽象出来,由子类实现不同的具体实现。
  • 当需要控制子类的扩展时,可以使用模板方法模式。模板方法模式通过定义抽象类来规范子类的方法实现,子类必须遵从抽象类中定义的方法的规范,这样可以控制子类的扩展。
  • 如果需要一次性编写出框架的核心代码,而将具体实现留给子类来实现,可以使用模板方法模式。

模式代码实现

  下面通过一个简单的示例来说明模板方法模式的实现。

  假设我们需要开发一个系统,实现计算机基准测试的功能。我们可以定义一个Benchmark类来表示基准测试,其中包括start()run()stop()三个抽象方法,分别用于启动测试、执行测试和结束测试。具体的测试算法可以由子类来实现。

package com.example.javaDesignPattern.templateMethod;

/**
 * @author bug菌
 * @version 1.0
 * @date 2023/9/20 15:44
 */
public abstract class Benchmark {
    public void runBenchmark() {
        start();
        for (int i = 0; i < 10; i++) {
            run();
        }
        stop();
    }

    public abstract void start();

    public abstract void run();

    public abstract void stop();
}

我们可以定义一个具体的子类来实现具体的测试算法,如下所示:

package com.example.javaDesignPattern.templateMethod;

/**
 * @author bug菌
 * @version 1.0
 * @date 2023/9/20 15:44
 */
public class ConcreteBenchmark extends Benchmark {
    @Override
    public void start() {
        System.out.println("启动基准测试");
    }

    @Override
    public void run() {
        System.out.println("执行基准测试");
    }

    @Override
    public void stop() {
        System.out.println("结束基准测试");
    }
}

  其中定义了一个基准测试的抽象类Benchmark,其中包含了一个模板方法,模板方法定义了基本操作的顺序和流程,具体的操作由子类实现。

  具体的子类ConcreteBenchmark重写了三个抽象方法startrunstop,其中start方法启动了基准测试,run方法执行了基准测试,stop方法结束了基准测试。

  在具体的子类中,可以实现具体的基准测试,而模板方法中定义的流程保证了基准测试的正确性和可维护性。这种设计模式可以减少代码重复,提高代码的可读性和可维护性。

  然后你在使用时,我们可以先创建一个Benchmark对象,然后调用它的runBenchmark()方法,即可执行具体的测试算法。

package com.example.javaDesignPattern.templateMethod;

/**
 * @author bug菌
 * @version 1.0
 * @date 2023/9/20 15:45
 */
public class Client {
    public static void main(String[] args) {
        Benchmark benchmark = new ConcreteBenchmark();
        benchmark.runBenchmark();
    }
}

执行结果如下:

在这里插入图片描述

代码解读:

  如上代码,定义了一个名为Client的类,其中包含一个名为main的公共静态方法。当程序运行时,将创建一个ConcreteBenchmark对象,该对象实现了Benchmark接口,并将其赋值给类型为Benchmarkbenchmark变量。接下来,runBenchmark方法将被调用来执行基准测试。

附录源码

  如上涉及代码均已上传同步在GitHub,提供给同学们参考性学习。

总结

  模板方法模式是一种基于继承的设计模式,它通过一系列抽象方法和模板方法来定义算法骨架,而由具体的子类来实现这些抽象方法,从而完成对算法的具体实现。模板方法模式可以很好地解决代码复用、扩展性和屏蔽细节等问题。在实际应用中,模板方法模式比较常用,比如在框架设计、算法设计等方面都有广泛的应用。

☀️建议/推荐你


  如果想系统性的全面学习设计模式,建议小伙伴们直接毫无顾忌的关注这个专栏《聊设计模式》,无论你是想提升自己的编程技术,还是渴望更好地理解代码背后的设计思想,本专栏都会为你提供实用的知识和启发,帮助你更好地解决日常开发中的挑战,将代码变得更加优雅、灵活和可维护!

📣关于我


我是bug菌,CSDN | 掘金 | infoQ | 51CTO 等社区博客专家,历届博客之星Top30,掘金年度人气作者Top40,51CTO年度博主Top12,华为云 | 阿里云| 腾讯云等社区优质创作者,全网粉丝合计15w+ ;硬核微信公众号「猿圈奇妙屋」,欢迎你的加入!免费白嫖最新BAT互联网公司面试题、4000G pdf电子书籍、简历模板等海量资料。

更多推荐

Pluma 插件管理框架

1.概述Pluma是一个用C++开发的可用于管理插件的开源架构,其官网地址为:http://pluma-framework.sourceforge.net/。该架构是个轻量级架构,非常易于理解。Pluma架构有以下基本概念:1)插件的外在行为体现为一个纯虚类,可以叫作插件接口;2)继承于同一个插件接口的若干派生类,被认

异地远程访问本地SQL Server数据库【无公网IP内网穿透】

文章目录1.前言2.SeaFile云盘设置2.1Owncould的安装环境设置2.2SeaFile下载安装2.3SeaFile的配置3.cpolar内网穿透3.1Cpolar下载安装3.2Cpolar的注册3.3Cpolar云端设置3.4Cpolar本地设置4.公网访问测试5.结语1.前言现在我们身边的只能设备越来越多

工作、生活常用免费api接口大全

手机号码归属地:提供三大运营商的手机号码归属地查询。全国快递物流查询:1.提供包括申通、顺丰、圆通、韵达、中通、汇通等600+快递公司在内的快递物流单号查询。2.与官网实时同步更新。3.自动识别快递公司。IP归属地-IPv4区县级:根据IP地址查询归属地信息,包含43亿全量IPv4,支持到中国地区(不含港台地区)区县级

弹跳小球-第15届蓝桥杯第一次STEMA测评Scratch真题精选

[导读]:超平老师的《Scratch蓝桥杯真题解析100讲》已经全部完成,后续会不定期解读蓝桥杯真题,这是Scratch蓝桥杯真题解析第152讲。第15届蓝桥杯第1次STEMA测评已于2023年8月20日落下帷幕,编程题一共有6题,分别如下:行走的螃蟹飞驰的高铁旋转的正方体弹跳小球比较身高数据计算弹跳小球,本题是202

每天一道大厂SQL题【Day26】脉脉真题实战(二)活跃时长的均值

文章目录每天一道大厂SQL题【Day26】脉脉真题实战(二)活跃时长的均值每日语录第26题中级题:活跃时长的均值1.需求列表思路分析答案获取加技术群讨论附表文末SQL小技巧后记每天一道大厂SQL题【Day26】脉脉真题实战(二)活跃时长的均值大家好,我是Maynor。相信大家和我一样,都有一个大厂梦,作为一名资深大数据

测试用例设计底层逻辑

【软件测试行业现状】2023年了你还敢学软件测试?未来已寄..测试人该何去何从?【自动化测试、测试开发、性能测试】测试用例是每位测试人员都绕不开的话题,也是大家习以为常的事情。几乎所有测试相关的公众号、博客、专栏,都会提及测试用例,由此可见它的重要性。但是,有许多从业者,对测试用例的设计仍然依靠经验积累,即使知道用例要

持安科技孙维伯:零信任理念下的实战攻防:ISC2023数字小镇演讲

近日,在ISC2023第十一届互联网安全大会上,持安科技联合创始人孙维伯作为零信任办公安全赛道代表,亮相数字小镇New50,并发表《全方位防御:零信任理念下的实战攻防》主题演讲。以下是本次演讲实录:这几年,网络安全已经从监管合规趋向于实战化,网络诈骗、黑产越发猖獗,企业面临的安全挑战愈加严峻。在实战攻防的场景下,攻防双

Nginx 服务器 SSL 证书安装部署

操作场景本文档指导您如何在Nginx服务器中安装SSL证书。说明本文档以证书名称xxx为例。Nginx版本以nginx/1.18.0为例。当前服务器的操作系统为CentOS7,由于操作系统的版本不同,详细操作步骤略有区别。安装SSL证书前,请您在Nginx服务器上开启HTTPS默认端口443,避免证书安装后无法启用HT

2、从“键鼠套装”到“全键盘游戏化”审核

1、风行内容仓的增效之路-前言内容仓成立初期,安全审核组是规模最大的小组,占到部门人数的半壁江山,因此增效工作首先就从安全审核开始。早期安全审核每天的达标值在800条左右,每天的总审核量不到1万,距离业务部门期望的数量差距较大。我找到相关同事,讨论如何提高每天的审核产出,同事反馈说,感觉没有什么方法,部门内部已经做过测

孙宇晨出席米尔肯研究院亚洲峰会:持续推动行业破圈 亚洲将成重要加密中心

9月14日,波场TRON创始人、火币HTX全球顾问委员会成员孙宇晨受邀出席2023米尔肯研究院亚洲峰会(2023MilkenInstituteAsiaSummit),与前美国驻新加坡大使、WagarGlobalAdvisors咨询公司主席KirkWagar就加密行业未来趋势相关问题进行了深度对话。孙宇晨在对谈中表示,稳

DETR 系列 Mask Frozen-DETR: High Quality Instance Segmentation with One GPU 论文阅读笔记

DETR系列MaskFrozen-DETR:HighQualityInstanceSegmentationwithOneGPU论文阅读笔记一、Abstract二、引言三、相关工作目标检测实例分割讨论四、本文的方法4.1Baseline设置结果实验设置4.2图像特征编码器DeformableencoderblockSwi

热文推荐