设计模式--模板方法外观模式

模板方法模式

场景:需使用代码方式实现,考完试后,将各个学生的试卷及答案誊抄一份。

假如有两个学生的试卷誊抄完毕.

// 学生A
public class TestPaperA {
    // 试题1
    public void testQuestion1() {
        System.out.println("问题一:XXXXXXXX[] A.xx B.xx C.xx D.xx ");
        System.out.println("答案 A");
    }
    // 试题2
    public void testQuestion2() {
        System.out.println("问题二:XXXXXXXX[] A.xx B.xx C.xx D.xx ");
        System.out.println("答案 A");
    }
    // 试题3
    public void testQuestion3() {
        System.out.println("问题三:XXXXXXXX[] A.xx B.xx C.xx D.xx ");
        System.out.println("答案 A");
    }
}
// 学生B
public class TestPaperB {
    // 试题1
    public void testQuestion1() {
        System.out.println("问题一:XXXXXXXX[] A.xx B.xx C.xx D.xx ");
        System.out.println("答案 B");
    }
    // 试题2
    public void testQuestion2() {
        System.out.println("问题二:XXXXXXXX[] A.xx B.xx C.xx D.xx ");
        System.out.println("答案 B");
    }
    // 试题3
    public void testQuestion3() {
        System.out.println("问题三:XXXXXXXX[] A.xx B.xx C.xx D.xx ");
        System.out.println("答案 B");
    }
}
  • 客户端
System.out.println("学生A的试卷");
TestPaperA a = new TestPaperA();
a.testQuestion1();
a.testQuestion2();
a.testQuestion3();

System.out.println("学生B的试卷");
TestPaperB b = new TestPaperB();
b.testQuestion1();
b.testQuestion2();
b.testQuestion3();

一眼看出,很多重复的代码,直接进行提炼抽离。此例中,试卷都是一样的,而答案是不同的,我们直接将重复的代码提炼,然后学生去继承它即可。

  • 试卷类
// 试卷类
public abstract class TestPaper { 
    // 3道题的答案
    protected abstract String answer1();
    protected abstract String answer2();
    protected abstract String answer3();

    // 试题1
    public void testQuestion1() {
        System.out.println("问题一:XXXXXXXX[] A.xx B.xx C.xx D.xx ");
        System.out.println("答案 " + answer1());
    }
    // 试题2
    public void testQuestion2() {
        System.out.println("问题二:XXXXXXXX[] A.xx B.xx C.xx D.xx ");
        System.out.println("答案 " + answer2());
    }
    // 试题3
    public void testQuestion3() {
        System.out.println("问题三:XXXXXXXX[] A.xx B.xx C.xx D.xx ");
        System.out.println("答案 " + answer3());
    }  
}

学生类只需要继承它,然后填写自己的答案即可。因为父类已经建立好了所有重复的模板

// 学生A
public class TestPaperA extends TestPaper{
    @Override
    protected String answer1() {
        return "A";
    }
    @Override
    protected String answer2() {
        return "A";
    }
    @Override
    protected String answer3() {
        return "A";
    }
}
  • 客户端
System.out.println("学生A的试卷");
TestPaper a = new TestPaperA();
a.testQuestion1();
a.testQuestion2();
a.testQuestion3();

那么上述的例子中,用的一种设计模式就是模板方法模式。定义一个操作中的算法的骨架,而将一些步骤延迟到子类中。模板方法使得子类可以不改变一个算法的结构即可重新定义该算法的某些特定步骤。

结构图及代码示例如下:

在这里插入图片描述

public abstract class AbstractClass {
    
    // 模板方法(所有重复的代码都放入这里)
    public void templateMethod() {
        ...
    }
    
    // 子类的特定实现
    public abstract void primitiveOperation1();
    public abstract void primitiveOperation2();
    
}
  • 子类
public class ConcreteClassA extends AbstractClass {
    @Override
    public void primitiveOperation1() {
        System.out.println("A类具体实现一");
    }

    @Override
    public void primitiveOperation2() {
        System.out.println("A类具体实现二");
    }
}

模板方法是通过把不变行为搬到父类(超类),去除子类中重复代码来体现它的优势。

模板方法是提供了一个代码复用平台。

当不变的和可变行为在方法的实现中混合在一起的时候,不变行为就会在类中重复出现。我们通过模板方法将这些行为搬移到单一的地方,这样帮助子类摆脱重复的不变行为的纠缠。

外观模式

以一个股票买卖的例子来理解一下,现在有股票、国债、房产,买入卖出代码如下:

  • 股票
// 股票1
public class Stock1 {
    public void buy() {
        System.out.println("股票1买入");
    }
    public void sell() {
        System.out.println("股票1卖出");
    }
}
// 股票2
class Stock2 {
    public void buy() {
        System.out.println("股票2买入");
    }
    public void sell() {
        System.out.println("股票2卖出");
    }
}
  • 国债、房产
// 国债1
public class NationalDebt1 {
    public void buy() {
        System.out.println("国债买入");
    }
    public void sell() {
        System.out.println("国债卖出");
    }
}

// 房产
class Realty1 {
    public void buy() {
        System.out.println("房产买入");
    }
    public void sell() {
        System.out.println("房产卖出");
    }
}
  • 客户端
Stock1 stock1 = new Stock1();
Stock2 stock2 = new Stock2();
NationalDebt1 nd1 = new NationalDebt1();
Realty1 rt1 = new Realty1();

// 买入
stock1.buy();
stock2.buy();
nd1.buy();
rt1.buy();

// 卖出
stock1.sell();
stock2.sell();
nd1.sell();
rt1.sell();

外观模式

增加一个基金类,结构图

在这里插入图片描述

  • 基金类代码
public class Fund {
    Stock1 stock1;
    Stock2 stock2;
    NationalDebt1 nd1;
    Realty1 rt1;
    public Fund() {
        stock1 = new Stock1();
        stock2 = new Stock2();
        nd1 = new NationalDebt1();
        rt1 = new Realty1();
    }
    public void buyFund() {
        stock1.buy();
        stock2.buy();
        nd1.buy();
        rt1.buy();
    }
    public void sellFund() {
        stock1.sell();
        stock2.sell();
        nd1.sell();
        rt1.sell();
    }
    
}
  • 客户端
Fund fund = new Fund();
fund.buyFund();

fund.sellFund();

外观模式:为子系统中的一组接口提供一个一致的界面,此模式定义了一个高层接口,这个接口使得这一子系统更加容易使用。

首先在设计阶段,应该有意识将不同的两个层进行分离。其次,在开发阶段,子系统往往因为不断的重构演化而变得越来越复杂,增加外观模式可以提供一个简单的接口减少它们之间的依赖。

还可以在新系统中使用外观模式,创建一个Facade类(外观模式类),来提供设计粗糙或高复杂度的遗留代码的比较清晰简单的接口,让新系统与Facade对象交互,Facade与遗留代码交互完成复杂的工作。

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

一文搞懂RC滤波器的设计?

滤波器是一种可以对“波”进行过滤的器件,一般是特定频率的信号。所以可以常常看到滤波器的种类繁多,有高通滤波器,低通滤波器,带通滤波器及带阻滤波器等等。 滤波器的主要作用就是滤波,它需要尽可能的让有用信号能够做…

九. Linux网络命令

网络命令write 网络命令wall 网络命令ping 首先,ping程序会向域名服务器(DNS)发送请求,解析域名www.baidu.com的IP地址。DNS返回域名的一个别名www.a.shifen.com以及对应的IP地址183.2.172.185。之后ping程序开始向这个地址发送请求报文,每1s…

大模型重塑软件设计,南京真我加入飞桨技术伙伴,大模型生态圈成员又添一员!...

为帮助伙伴更快、更好的应用大模型技术,飞桨技术伙伴体系及权益基于星河共创计划全面升级,通过丰富的场景、技术、算力、品牌等资源,为伙伴企业提供一站式的大模型资源对接,全面降低创建AI原生应用的门槛。 近日,南京真…

C 语言字符串

C 语言字符串 在本教程中,您将学习C语言编程中的字符串。您将在示例的帮助下学习声明它们,对其进行初始化以及将它们用于各种 I / O(输入/输出)操作。 在C语言编程中,字符串是以null字符\0结束的字符序列。例如: ch…

电子学会2023年06月青少年软件编程(图形化)等级考试试卷(一级)真题,含答案解析

青少年软件编程(图形化)等级考试试卷(一级) 一、单选题(共25题,共50分) 1. 看图找规律,请问下图红框中是?( ) A.

京东数据采集与挖掘(京东大数据):2023年10月京东冰箱品牌销售排行榜

鲸参谋监测的京东平台10月份冰箱市场销售数据已出炉! 10月份,冰箱市场的销售额有小幅上涨。鲸参谋数据显示,在京东平台上,今年10月冰箱市场的销量为94万,销售额将近23亿,同比增长超过1%。从价格上看&#x…

Flume学习笔记(1)—— Flume入门

Flume 概述 Flume 是 Cloudera 提供的一个高可用的,高可靠的,分布式的海量日志采集、聚合和传输的系统 Flume 基于流式架构,灵活简单 Flume最主要的作用就是,实时读取服务器本地磁盘的数据,将数据写入到HDFS 基础架…

4.3每日一题(知全微分求函数本身)

公式 1、先通过公式:dx前系数对y求偏导、dy前面的系数对x求偏导,求出 f(x)的表达式;对x求不定积分,再通过 f(0)0求出常数C,即可求出 f(x) 2、把F(x)的全微分列出来,dx、dy前面的表达式分别为F(x)偏x、y的…

数据库编程sqlite3库安装及使用

数据库编程 数据库的概念 数据库是“按照数据结构来组织、存储和管理数据的仓库”。是一个长期存储在计算机内的、有组织的、可共享的、统一管理的大量数据的集合。 数据库是存放数据的仓库。它的存储空间很大,可以存放百万条、千万条、上亿条数据。但是数据库并不是…

在python中os.chdir()的含义以及用法

文章目录 一、os.chdir() 是什么?二、用法注意 一、os.chdir() 是什么? 在Python中,os.chdir() 是 “change directory” 的缩写,意思是改变当前工作目录。这个函数是Python的 os 模块的一部分,允许你更改程序的工作目…

CTF-虚拟机——【前置知识二】

文章目录 CPU虚拟化特权级压缩权限系统虚拟化解决方法模拟&解释执行(VMware)扫描&修补二进制翻译(Binary Translation)二进制代码翻译技术与扫描修补技术区别硬件辅助虚拟化技术(VT)VMX操作模式&am…

在线 sha1 加密

ttmd5 http://www.ttmd5.com/hash.php?type5 qqxiuzi https://www.qqxiuzi.cn/bianma/sha-1.htm jb51 http://tools.jb51.net/password/sha_encode

vue3安装vue-router

环境 node 18.14.2 yarn 1.22.19 windows 11 vite快速创建vue项目 参考 安装vue-touter 官网 yarn add vue-router4src下新建router文件夹,该文件夹下新建index.ts // router/index.ts 文件 import { createRouter, createWebHashHistory, RouterOptions, Ro…

浅谈霍尔电流传感器在UPS蓄电池浮充电流远程监测方案的应用-安科瑞 蒋静

摘要:针对无人平台UPS蓄电池多次出现浮充电流过高的现象,介绍了UPS系统的结构和工作原理,通过应用霍尔电流传感器,DCS组态,实现UPS蓄电池浮充电流远程监控,异常电流故障报警,推动了无人平台的自…

《向量数据库指南》——TruLens + Milvus Cloud构建RAG深入了解性能

深入了解性能 索引类型 本例中,索引类型对查询速度、token 用量或评估没有明显影响。这可能是因为数据量较小的关系。索引类型对较大语料库可能更重要。 Embedding 模型 text-embedding-ada-002 在准确性(0.72,平均 0.60)和答案相关度(0.82,平均0.62)上优于 MiniLM Embeddin…

BUUCTF [GXYCTF2019]佛系青年 1

BUUCTF:https://buuoj.cn/challenges 题目描述: 密文: 下载附件,解压得到ZIP压缩包。 解题思路: 1、压缩包内有一张png图片和一个txt文本,解压zip压缩包,解压出图片,但txt文本提示需要输入密…

ElementUI及ElementUI Plus Axure RP高保真交互元件库及模板库

基于ElementUI2.0及ElementUI Plus3.0二次创作的ElementUI 元件库。2个版本的原型图内容会有所不同,ElementUI Plus3.0的交互更加丰富和高级。你可以同时使用这两个版本。 不仅包含Element UI 2.0版,还包含Element Plus 3版本。Element 2版支持Axure 8&…

vue+element实现多级表头加树结构

标题两种展示方式 方式一 完整代码: <template><div class"box"><el-tableref"areaPointTable":data"tableData"border:span-method"objectSpanMethod":header-cell-style"tableHeaderMerge"><el-ta…

Nacos 配置中心底层原理(1.X版本)

前言 Nacos 1.X版本 是长轮询 Nacos 2.X版本 是GRPC 长轮询 概念 客户端会轮询向服务端发出一个长连接请求&#xff0c;这个长连接最多30s就会超时&#xff0c;服务端收到客户端的请求会先判断当前是否有配置更新&#xff0c;有则立即返回&#xff0c;如果没有服务端会将这个…

第三方付支付-聚合支付系统设计方案

第三方付支付-聚合支付系统设计方案 阅读须知&#xff1a;本文仅针对聚合支付平台的核心功能架构基本概要,不涉及技术方案 目录&#xff1a;渠道管理&#xff0c;订单管理&#xff0c;对账管理&#xff0c;商家管理&#xff0c;代理管理&#xff0c;账号管理&#xff0c;风控…