设计模式浅析(六) ·命令模式

设计模式浅析(六) ·命令模式

日常叨逼叨

java设计模式浅析,如果觉得对你有帮助,记得一键三连,谢谢各位观众老爷😁😁


命令模式

概念

命令模式(Command Pattern)是一种行为设计模式,它允许将请求封装为一个对象,从而使你可以使用不同的请求将客户端与接收者解耦。命令模式也支持可撤销操作。

命令模式结构

命令模式(Command Pattern)的结构包含以下四个主要角色:

  1. Command(命令接口)
    • 定义了一个用于执行请求的接口。命令对象通常会持有接收者对象,并在调用时执行其上的操作。
  2. ConcreteCommand(具体命令类)
    • 实现了命令接口,通常会持有一个接收者对象,并定义了一个execute方法来执行请求。
    • 具体命令类知道如何执行与接收者相关联的动作,通常动作实现在接收者对象中,但命令对象决定了何时执行动作。
  3. Receiver(接收者)
    • 知道如何执行与命令相关联的具体操作。任何类都可能成为接收者,只要它能实现执行请求所需的操作。
  4. Invoker(调用者)
    • 也称为请求者,它负责调用命令对象来执行请求。
    • 调用者并不直接知道接收者的存在,也不直接与接收者交互。它通过命令对象来间接调用接收者。
  5. Client(客户端)
    • 创建具体命令对象,并设置给调用者。
    • 客户端负责组装命令对象,但并不直接调用接收者。
命令模式类图

请添加图片描述

示例

我们将模拟使用命令模式实现一个电视开关机Demo。电视遥控器操作有许多种,Demo实现电视的开机和关机两种操作,使用命令模式完成,方便后续其他操作模式的拓展。

根据上述命令模式的结构,首先创建一个命令接口,在抽象命令中,具有一个execute()方法,待会的具体命令将实现这个execute()方法。

//抽象命令接口
public interface Command {//命令执行void execute() throws InterruptedException;}

接着,我们需要定义一个命令的接收者,即负责处理命令的具体逻辑操作。在这个类中,我们定义了两种操作的方法,分别是on()off()。在两个方法中分别输出打开和关闭

public class TVCommandReceiver {public void on() throws InterruptedException {System.out.println("turn on tv");Thread.sleep(2000);System.out.println("now tv is on");}public void off() throws InterruptedException {System.out.println("turn off tv ");Thread.sleep(2000);System.out.println("now tv is off");}
}

然后实现具体的命令,CommandOn类实现了Command命令的execute()方法,并且管理了一个命令接收者实例,方便调用者Invoker进行调用

public class CommandOn implements Command{TVCommandReceiver tvCommandReceiver;public CommandOn(TVCommandReceiver tvCommandReceiver) {this.tvCommandReceiver = tvCommandReceiver;}@Overridepublic void execute() throws InterruptedException {tvCommandReceiver.on();}}

CommandOff与CommandOn相类似

public class CommandOff implements Command{TVCommandReceiver tvCommandReceiver;public CommandOff(TVCommandReceiver tvCommandReceiver) {this.tvCommandReceiver = tvCommandReceiver;}@Overridepublic void execute() throws InterruptedException {tvCommandReceiver.off();}}

最后,我们要实现一个命令的调用者即Invoker类,该类中含有添加命令和命令执行的具体逻辑。并管理了一个命令列表,方便记录历史。

在Invoker类中,我们实现了三个方法,分别是putCommand()runCommand()cancelCommand()putCommand()方法会将所有命令加入到命令列表中。而runCommand()方法将遍历所有命令,负责执行具体命令,cancelCommand()用于执行时取消某个命令。

public class Invoker {private List<Command> commandList = new ArrayList<>();/**** 添加命令* @param command*/public void putCommand(Command command) {commandList.add(command);}/**** 执行命令* @throws InterruptedException*/public void runCommand() throws InterruptedException {if (commandList.size() == 0) {System.out.println("no command input");}for (Command command : commandList) {command.execute();}commandList.clear();}/**** 取消命令* @param command*/public void cancelCommand(Command command) {if (commandList.size() == 0) {System.out.println("no command input");}int index = commandList.indexOf(command);if (index == -1) {System.out.println("no such command find ");} else {commandList.remove(index);System.out.println("command " + command + "has been canceled");}}
}

至此,尝试创建Client进行测试

public class Client {public static void main(String[] args) throws InterruptedException {//注册命令接收者TVCommandReceiver receiver = new TVCommandReceiver();//注册命令CommandOn tvOnCommand = new CommandOn(receiver);CommandOff tvOffCommand = new CommandOff(receiver);//添加命令Invoker invoker = new Invoker();invoker.putCommand(tvOnCommand);invoker.putCommand(tvOffCommand);//取消命令invoker.cancelCommand(tvOffCommand);//命令执行invoker.runCommand();}
}

执行结果:

command com.jerry.commandPattern.CommandOff@1b6d3586has been canceled
turn on tv
now tv is on

Process finished with exit code 0

至此,我们实现了简单的命令模式案例

优缺点
优点
  1. 降低耦合度:命令模式可以将请求者与接收者解耦,调用者只需要知道如何调用命令,而不需要知道命令的具体实现细节。
  2. 扩展性良好:增加或删除命令非常方便,满足“开闭原则”。由于增加新的命令类不会影响到其他类,因此系统具有良好的扩展性。
  3. 支持宏命令:命令模式可以与组合模式结合,将多个命令装配成一个组合命令(宏命令),从而可以一次性执行多个操作。
  4. 支持撤销和重做:命令模式可以与备忘录模式结合,实现命令的撤销与恢复操作,方便实现撤销(Undo)和重做(Redo)功能。
缺点
  1. 命令类过多:如果系统中有大量的命令,那么就需要创建大量的命令类,这可能会导致系统结构变得复杂,增加理解和维护的难度。
  2. 可能导致性能问题:如果命令的执行过程比较复杂,那么频繁地创建和销毁命令对象可能会对系统的性能产生负面影响。
  3. 客户端代码可能变得复杂:如果客户端需要创建和管理大量的命令对象,那么客户端代码可能会变得复杂和难以维护。

代码相关代码可以参考 代码仓库🌐

ps:本文原创,转载请注明出处


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

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

相关文章

集合、List、Set、Map、Collections、queue、deque

概述 相同类型的数据进行统一管理操作&#xff0c;使用数据结构、链表结构&#xff0c;二叉树 分类&#xff1a;Collection、Map、Iterator 集合框架 List接口 有序的Collection接口&#xff0c;可以对列表中的每一个元u尿素的插入位置进行精确的控制&#xff0c;用户可以根…

如何在 VM 虚拟机中安装 Windows XP 操作系统保姆级教程(附链接)

一、VMware Workstation 虚拟机 没有安装 VM 虚拟机的参考以下文章进行安装&#xff1a; VM 虚拟机安装教程https://eclecticism.blog.csdn.net/article/details/135713915 二、Windows XP 镜像 点击链接下载镜像 下载链接https://pan.baidu.com/s/1sk5pU8PoTJ1dOxMpGCUfc…

【前端】夯实基础 css/html/js 50个练手项目(持续更新)

文章目录 前言Day 1 expanding-cardsDay 2 progress-stepsDay 7 Split Landing PageDay9 Sound BoardDay10 Dad Jokes 前言 发现一个没有用前端框架的练手项目&#xff0c;很适合我这种纯后端开发夯实基础&#xff0c;内含50个mini project&#xff0c;学习一下&#xff0c;做…

[服务器-数据库]MongoDBv7.0.4不支持ipv6访问

文章目录 MongoDBv7.0.4不支持ipv6访问错误描述问题分析错误原因解决方式 MongoDBv7.0.4不支持ipv6访问 错误描述 报错如下描述 Cannot connect to MongoDB.No suitable servers found: serverSelectionTimeoutMS expired: [failed to resolve 2408]问题分析 首先确定其是…

【Python从入门到进阶】49、当当网Scrapy项目实战(二)

接上篇《48、当当网Scrapy项目实战&#xff08;一&#xff09;》 上一篇我们正式开启了一个Scrapy爬虫项目的实战&#xff0c;对当当网进行剖析和抓取。本篇我们继续编写该当当网的项目&#xff0c;讲解刚刚编写的Spider与item之间的关系&#xff0c;以及如何使用item&#xff…

DIcom调试Planar configuration

最近和CBCT组同事调dicom图像 这边得图像模块老不兼容对方得dicom文件。 vtk兼容&#xff0c;自己写得原生解析不兼容。 给对方调好了格式&#xff0c;下次生成文件还会有错。 简单记录下&#xff0c;日后备查。 今天对方又加了 个字段&#xff1a;Planar configuration 查…

计算机网络-网络互联

文章目录 网络互联网络互联方法LAN-LAN&#xff1a;网桥及其互连原理使用网桥实现LAN-LAN使用交换机扩展局域网使用路由器连接局域网 LAN-WANWAN-WAN路由选择算法非自适应路由选择算法自适应路由选择算法广播路由选择算法&#xff1a;分层路由选择算法 网络互联 网络互联是指利…

【安装记录】解决ssh密码正确,却无法连接到虚拟机

可能是没有允许Root登录 解决办法&#xff1a;修改/etc/ssh/sshd_config文件&#xff0c;将 PermitRootLogin 项打开

AI大模型与小模型之间的“脱胎”与“反哺”(第一篇)

一、AI小模型脱胎于AI大模型&#xff0c;而AI小模型群又可以反哺AI大模型 AI大模型&#xff08;如GPT、BERT等&#xff09;通常拥有大量的参数和训练数据&#xff0c;能够生成或理解复杂的文本内容。这些大模型在训练完成后&#xff0c;可以通过剪枝、微调等方式转化为小模型&…

WordPres Bricks Builder 前台RCE漏洞复现(CVE-2024-25600)

0x01 产品简介 Bricks Builder是一款用于WordPress的开发主题,提供直观的拖放界面,用于设计和构建WordPress网站。它使用户能够轻松创建自定义的网页布局和设计,无需编写或了解复杂的代码。Bricks Builder具有用户友好的界面和强大的功能,使用户可以通过简单的拖放操作添加…

在autodl搭建stable-diffusion-webui+sadTalker

本文介绍在autodl.com搭建gpu服务器&#xff0c;实现stable-diffusion-webuisadTalker功能&#xff0c;图片音频 可生成视频。 autodl租GPU 自己本地部署SD环境会遇到各种问题&#xff0c;网络问题&#xff08;比如huggingface是无法访问&#xff09;&#xff0c;所以最好的方…

qt-C++笔记之事件过滤器

qt-C笔记之事件过滤器 —— 杭州 2024-02-25 code review! 文章目录 qt-C笔记之事件过滤器一.使用事件过滤器和不使用事件过滤器对比1.1.使用事件过滤器1.2.不使用事件过滤器1.3.比较 二.Qt 中事件过滤器存在的意义三.为什么要重写QObject的eventFilter方法&#xff1f;使用QO…

【服务器数据恢复】通过reed-solomon算法恢复raid6数据的案例

服务器数据恢复环境&#xff1a; 一台网站服务器中有一组由6块磁盘组建的RAID6磁盘阵列&#xff0c;操作系统层面运行MySQL数据库和存放一些其他类型文件。 服务器故障&#xff1a; 该服务器在工作过程中&#xff0c;raid6磁盘阵列中有两块磁盘先后离线&#xff0c;不知道是管理…

力扣--动态规划1027.最长等差数列

思路分析&#xff1a; 使用动态规划的思想&#xff0c;定义二维数组dp&#xff0c;其中dp[i][j]表示以nums[i]为结尾&#xff0c;公差为(j-1000)的等差数列长度。为了适应负数的情况&#xff0c;将公差的范围设为[-1000, 1000]&#xff0c;并且加上1000作为数组索引。 初始化r…

2024年环境安全科学、材料工程与制造国际学术会议(ESSMEM2024)

【EI检索】2024年环境安全科学、材料工程与制造国际学术会议&#xff08;ESSMEM2024) 会议简介 我们很高兴邀请您参加将在三亚举行的2024年环境安全科学、材料工程和制造国际学术会议&#xff08;ESSMEM 2024&#xff09;。 ESSMEM2024将汇集世界各国和地区的研究人员&…

HarmonyOS创建一个ArkTS卡片

创建一个ArkTS卡片 在已有的应用工程中&#xff0c;创建ArkTS卡片&#xff0c;具体操作方式如下。 创建卡片。 根据实际业务场景&#xff0c;选择一个卡片模板。 在选择卡片的开发语言类型&#xff08;Language&#xff09;时&#xff0c;选择ArkTS选项&#xff0c;然后单…

vscode使用restClient实现各种http请求

vscode使用restClient实现各种http请求 一&#xff0c;安装插件 首先&#xff0c;我们要在vscode的扩展中&#xff0c;搜索rest Client&#xff0c;然后安装它&#xff0c;这里我已经安装过了。 安装后&#xff0c;我们就可以使用rest client插件进行http各种操作了。 二&…

项目解决方案:街道社区视频监控接入、汇聚和联网设计方案

目 录 一、客户需求 二、网络拓扑图 三、方案描述 四、系统配置 1、服务器配置 2、带宽配置 五、方案优势 1. 平台可堆叠使用 2. 支持主流接入协议 4. 多种终端显示 5. 客户端功能强大 6. 一机一档 一、客户需求 1&#xff0c;一个街道有十个社…

Orange3数据预处理(列选择组件)数据角色及类型描述

在Orange3的文件组件中&#xff0c;datetime、categorical、numeric以及text代表不同种类的数据类型&#xff0c;具体如下&#xff1a; datetime&#xff1a;代表日期和时间类型的数据。通常用于时间序列分析、生存分析和其他需要考虑时间因素的机器学习任务中。例如&#xff0…

纽约纳斯达克大屏投放受众群体有哪些-大舍传媒

纽约纳斯达克大屏投放受众群体有哪些-大舍传媒 1. 纳斯达克大屏的概述 纳斯达克大屏是全球金融市场中最出名的电子交易平台之一。作为一个重要的金融信息传递渠道&#xff0c;纳斯达克大屏吸引了来自全球的投资者的目光。在这个巨大的投放平台上&#xff0c;大舍传媒希望为客…