当前位置: 首页 > news >正文

软件设计模式(三):责任链模式

前言

        前面荔枝梳理了有关单例模式、策略模式的相关知识,这篇文章荔枝将沿用之前的写法根据示例demo来体会这种责任链设计模式,希望对有需要的小伙伴有帮助吧哈哈哈哈哈哈~~~


文章目录

前言

责任链模式 

1 简单场景 

2 责任链模式理解 

 3 Java下servlet包中的doFilter

总结


责任链模式 

        责任链模式是将一系列处理单元通过指针连接起来,按顺序执行下去,完成对请求的处理,当责任链模式中一个处理单元不适合处理该请求时,将继续传递该请求到下一单元,其往往使用一个共享的上下文对象来包装请求,该上下文对象同样包含责任链的输出模型。责任链顺序执行的过程,是上下文输出模型逐渐完善的过程。

1 简单场景 

为了更好地理解,我们首先需要设计场景来理解:现在需要开发一个过滤机制来Msg对象中的非法输入,下面的代码是未使用责任链的模式。 

package com.crj.test;import java.util.ArrayList;
import java.util.List;public class SimpleMain {public static void main(String[] args) {Msg msg = new Msg();msg.setMsg("伪装一下注入:<script>关键词。。999......");List<Filter> filters = new ArrayList<>();filters.add(new HTMLFilter());filters.add(new SensitiveFilter());for(Filter f:filters){f.doFilter(msg);}System.out.println(msg);}
}class Msg{String name;String msg;public void setMsg(String msg) {this.msg = msg;}public String getMsg() {return msg;}@Overridepublic String toString() {return "Msg{" +"name='" + name + '\'' +", msg='" + msg + '\'' +'}';}}interface Filter{void doFilter(Msg m);
}/*** HTML过滤*/
class HTMLFilter implements Filter{@Overridepublic void doFilter(Msg m) {String r = m.getMsg();r = r.replace('<','[');r = r.replace('>',']');m.setMsg(r);}
}
/*** 敏感词过滤*/
class  SensitiveFilter implements Filter{@Overridepublic void doFilter(Msg m) {String r = m.getMsg();r = r.replace("999","666");m.setMsg(r);}
}

2 责任链模式理解 

        使用责任链模式来编写demo,可以看到我们添加了一个类FilterChain,通过该类中封装的add()方法来将不同的过滤规则进行添加,同时调用不同的规则对象各自声明的重写的doFilter方法实现过滤。这个过程就像是一串糖葫芦,一颗一颗需要用一根竹签串起来,这个竹签就是FilterChain类,糖葫芦就是不同的过滤规则类。

package com.crj.test;import java.util.ArrayList;
import java.util.List;public class SimpleMain {public static void main(String[] args) {Msg msg = new Msg();msg.setMsg("伪装一下注入:<script>关键词。。999......");FilterChain fc = new FilterChain();fc.add(new HTMLFilter());fc.add(new SensitiveFilter());fc.doFilter(msg);System.out.println(msg);}
}class Msg{String name;String msg;public void setMsg(String msg) {this.msg = msg;}public String getMsg() {return msg;}@Overridepublic String toString() {return "Msg{" +"name='" + name + '\'' +", msg='" + msg + '\'' +'}';}}interface Filter{void doFilter(Msg m);
}/*** HTML过滤*/
class HTMLFilter implements Filter{@Overridepublic void doFilter(Msg m) {String r = m.getMsg();r = r.replace('<','[');r = r.replace('>',']');m.setMsg(r);}
}
/*** 敏感词过滤*/
class  SensitiveFilter implements Filter{@Overridepublic void doFilter(Msg m) {String r = m.getMsg();r = r.replace("999","666");m.setMsg(r);}
}
/*** 过滤链*/
class FilterChain{List<Filter> filters = new ArrayList<>();public void add(Filter filter){filters.add(filter);}public void doFilter(Msg m){for(Filter f:filters){f.doFilter(m);}}
}

 3 Java下servlet包中的doFilter

        Java EEJDK中提供了一个在servlet包下的doFilter方法实现了责任链模式,具体的参数主要有三个:request、response和FilterChain类型的chain。该方法可以实现对于请求和响应同时进行过滤,即假设有一个请求打过来,三个过滤规则A、B、C按照A-B-C的顺序过滤,当请求响应后 发出的Response会按照C-B-A的规则过滤。这个过程的实现类似于递归算法。 

        我们可以通过这个图来理解这个方法中责任链调用的递归过程,每一次请求打在过滤类上进行处理完成后,就会调用doFilter()方法,并将指针指向下一个过滤类处理请求,下一个类处理后执行doFilter()方法查看是否index==责任链列表的长度,是的话就会返回并回退到上一个过滤类中的doFilter()方法执行并返回。 

按照需求我们需要自行封装Request和Response类、定义Filter类及其相应的实现类,封装的FilterChain类实现具体的责任链模式,demo如下:

package com.crj.test2;import java.util.ArrayList;
import java.util.List;public class ServletChain {public static void main(String[] args) {Request request = new Request();request.str = "大家好999<script>";Response response = new Response();response.str = "response";FilterChain chain = new FilterChain();chain.add(new HTMLFilter()).add(new SensitiveFilter());chain.doFilter(request,response,chain);}
}/*** 处理对象类*/
class Request{String str;
}
class Response{String str;
}/*** Filter接口*/
interface Filter{boolean doFilter(Request request,Response response,FilterChain chain);
}/*** 两个过滤类*/
class HTMLFilter implements Filter{@Overridepublic boolean doFilter(Request request, Response response,FilterChain chain) {request.str = request.str.replaceAll("<", "[").replaceAll(">", "]") + "HTMLFilter()";chain.doFilter(request, response, chain);response.str += "--HTMLFilter()";return true;}
}class SensitiveFilter implements Filter{@Overridepublic boolean doFilter(Request request, Response response,FilterChain chain) {request.str = request.str.replaceAll("996", "955") + " SensitiveFilter()";chain.doFilter(request, response, chain);response.str += "--SensitiveFilter()";return true;}
}/*** 责任链实现类*/
class FilterChain implements Filter{List<Filter> filters = new ArrayList<>();int index = 0;public FilterChain add(Filter f){filters.add(f);return this;}@Overridepublic boolean doFilter(Request request, Response response,FilterChain chain) {if(index==filters.size()) return false;Filter f = filters.get(index);index++;return f.doFilter(request,response,chain);}
}

文章主要使用的是马老师的课程中提供的案例,链接:

https://www.bilibili.com/video/BV1G44y1R7nv?p=14&vd_source=91c021af5a207c9fdf0bd7969d48cbf2


总结

        这篇文章中荔枝主要梳理了设计模式中的责任链模式的相关概念,在这里荔枝没有给出过多的概念性的东西而是侧重于代码场景来理解哈哈。设计模式荔枝学的好慢,最近课也多嘿,可能文章顺序发出来的有点乱。接下来荔枝也会持续学习并产出~~~一起加油转码ing~

今朝已然成为过去,明日依然向往未来!我是小荔枝,在技术成长的路上与你相伴,码文不易,麻烦举起小爪爪点个赞吧哈哈哈~~~ 比心心♥~~~

相关文章:

软件设计模式(三):责任链模式

前言 前面荔枝梳理了有关单例模式、策略模式的相关知识&#xff0c;这篇文章荔枝将沿用之前的写法根据示例demo来体会这种责任链设计模式&#xff0c;希望对有需要的小伙伴有帮助吧哈哈哈哈哈哈~~~ 文章目录 前言 责任链模式 1 简单场景 2 责任链模式理解 3 Java下servl…...

开发者的商业智慧:产品立项策划你知道多少?

文章目录 想法的萌芽&#x1f31f;初步评估产品可行性&#x1f34a;分析核心功能和特点以及竞争对手&#x1f4dd;大健康监测&#x1f4dd;时尚新科技产品&#x1f4dd;准确性&#x1f4dd;多功能&#x1f4dd;品牌口碑&#x1f4dd;数据分析与个性化建议&#x1f4dd;社交互动…...

Linux 6.6 初步支持AMD 新一代 Zen 5 处理器

AMD 下一代 Zen 5 CPU 现已开始为 Linux 6.6 支持提交相关代码&#xff0c;最新补丁包括提供温度监控和 EDAC 报告等。 最新的 Linux 6.6 代码中已经加入了包括支持硬件监视器温度监控和 EDAC 报告的补丁。此外&#xff0c;新版本还加入了 x86 / misc 补丁&#xff0c;Phoronix…...

第五章 Linux常用应用软件

第五章 Linux常用应用软件 ​ Ubuntu包含了日常所需的常用程序&#xff0c;集成了跨平台的办公套件LibreOffice和Mozila Firefox浏览器等。还提供了文本处理工具、图片处理工具等。 1.LibreOffice ​ LibreOffice免费开源&#xff0c;遵照GPL分发源代码&#xff0c;与OpenOf…...

连接云-边-端,构建火山引擎边缘云网技术体系

近日&#xff0c;火山引擎边缘云网络产品研发负责人韩伟在LiveVideoStack Con 2023上海站围绕边缘云海量分布式节点和上百T的网络规模&#xff0c;结合边缘云快速发展期间遇到的各种问题和挑战&#xff0c;分享了火山引擎边缘云网的全球基础设施&#xff0c;融合开放的云网技术…...

系统架构设计师(第二版)学习笔记----系统架构设计师概述

【原文链接】系统架构设计师&#xff08;第二版&#xff09;学习笔记----系统架构设计师概述 文章目录 一、架构设计师的定义、职责和任务1.1 架构设计师的定义1.2 架构设计师的任务 二、架构设计师应具备的专业素质2.1 架构设计师应具备的专业知识2.2 架构设计师的知识结构2.3…...

自动化测试:Selenium中的时间等待

在 Selenium 中&#xff0c;时间等待指在测试用例中等待某个操作完成或某个事件发生的时间。Selenium 中提供了多种方式来进行时间等待&#xff0c;包括使用 ExpectedConditions 中的 presence_of_element_located 和 visibility_of_element_located 方法等待元素可见或不可见&…...

vim 替换命令 “:s“

vim 替换命令 ":s" 1. 替换光标所在行的第一个匹配串2. 替换光标所在行全部匹配项3. 替换两行之间每行的第一个匹配项4. 替换两行之间的全部匹配项5. 替换整个文件中的每个匹配串6. 查找整个文件中的每个匹配串并询问是否替换 1. 替换光标所在行的第一个匹配串 命令…...

【golang】调度系列之m

调度系列 调度系列之goroutine 上一篇中介绍了goroutine&#xff0c;最本质的一句话就是goroutine是用户态的任务。我们通常说的goroutine运行其实严格来说并不准确&#xff0c;因为任务只能被执行。那么goroutine是被谁执行呢&#xff1f;是被m执行。 在GMP的架构中&#xff…...

可持久化线段树

可持久化线段树 模板 在某一指定版本的单点查&#xff0c;单点修。 开 m m m 棵线段树&#xff0c;每次修改复制后单点修。时间复杂度 O ( m ( n log ⁡ n ) ) O(m(n\log n)) O(m(nlogn))&#xff0c;空间复杂度 O ( n m ) O(nm) O(nm)&#xff0c;不如暴力。 每次修改…...

运行 Node.js 与浏览器 JavaScript

浏览器和 Node.js 都使用 JavaScript 软件语言 - 但字面上的运行时环境是不同的。 Node.js(又名服务器端 JavaScript)与客户端 JavaScript 有许多相似之处。它也有很多差异。 尽管两者都使用 JavaScript 作为软件语言,但我们可以重点关注一些关键差异,这些差异使两者之间…...

File类操作

1. 练习一 在当前模块下的 text 文件夹中创建一个 io.txt 文件 import java.io.File; import java.io.IOException;public class Practice1 {public static void main(String[] args) {File file new File("D:\\kaifamiao");File file1 new File(file, "tex…...

C# 实现电子签名

本项目基于Emgu.CV&#xff08;C#下OpenCv的封装&#xff09;开发的&#xff0c;编译器最新版Vs2022&#xff0c;编译环境x86 直接看效果图 1.主页面 2.我们先看手写的方式&#xff1a; 点击确认就到主界面&#xff0c;如下 &#xff1a; 点击自动适配-&#xff0c;再点击生成…...

小米6/6X/米8/米9手机刷入鸿蒙HarmonyOS.4.0系统-刷机包下载-遥遥领先

小米手机除了解锁root权限&#xff0c;刷GSI和第三方ROM也是米粉的一大爱好&#xff0c;这不&#xff0c;在华为发布了HarmonyOS.4.0系统后不久&#xff0c;我们小米用户也成功将自己的手机干山了HarmonyOS.4.0系统。虽然干上去HarmonyOS.4.0系统目前BUG非常多&#xff0c;根本…...

集合框架和泛型二

一、Set接口 1. Set接口概述 java.util.Set 不包含重复元素的集合、不能保证存储的顺序、只允许有一个 null。 public interface Set<E> extends Collection<E>抽象方法&#xff0c;都是继承自 java.util.Collection 接口。 Set 集合的实现类有很多&#xff0c;…...

thinkphp6 入门教程合集(更新中)

thinkphp6 入门&#xff08;1&#xff09;--安装、路由规则、多应用模式 thinkphp6 入门&#xff08;1&#xff09;--安装、路由规则、多应用模式_软件工程小施同学的博客-CSDN博客 thinkphp6 入门&#xff08;2&#xff09;--视图、渲染html页面、赋值 thinkphp6 入门&#…...

openGauss学习笔记-65 openGauss 数据库管理-创建和管理数据库

文章目录 openGauss学习笔记-65 openGauss 数据库管理-创建和管理数据库65.1 前提条件65.2 背景信息65.3 注意事项65.4 操作步骤65.4.1 创建数据库65.4.2 查看数据库65.4.3 修改数据库65.4.4 删除数据库 openGauss学习笔记-65 openGauss 数据库管理-创建和管理数据库 65.1 前提…...

mysql、MHA高可用配置即故障切换

MHA概述 一套优秀的MySQL高可用环境下故障切换和主从复制的软件 MHA的出现就是解决MySQL 单点的问题 MySQL故障过程中&#xff0c;MHA能做到0-30秒内自动完成故障切换 MHA能在故障切换的过程中最大程度上保证数据的一致性以达到真正意义上的高可用 MHA的组成&#xff08;核…...

使用“vue init mpvue/mpvue-quickstart“初始化mpvue项目时出现的错误及解决办法

当使用"vue init mpvue/mpvue-quickstart"初始化 mpvue 项目时出现 "vue-cli Failed to download repo mpvue/mpvue-quickstart: connect ETIMEDOUT IP地址"原因是 github 的 IP 解析失败&#xff0c;连接超时 解决办法&#xff1a;更改最新的 github 的 …...

Linux-Shell整理集合

Shell变量 参考文章&#xff1a; Shell脚本中变量的使用 shell语法之 , ‘ ‘ , {},, ,‘‘,(),$(())四种语法含义 参考文章&#xff1a; shell语法之 , ‘ ‘ , {},, ,‘‘,(),$(())四种语法含义 grep常用用法 Shell awk命令详解 grep 跟awk连着用&#xff1a; 获取某程序的…...

Linux性能优化之上下文切换

写在前面 上下文切换因为会导致消耗大量的CPU资源&#xff0c;导致CPU升高&#xff0c;所以上下文切换也是最常见的性能杀手之一。本文就一起来看下这部分内容吧。 1&#xff1a;基础内容介绍 1.1&#xff1a;什么是上下文切换&#xff1f; CPU在执行的时候需要两部分的内容…...

AI赋能51单片机开发:让快马平台智能生成复杂避障算法代码

最近在做一个基于51单片机的智能小车项目&#xff0c;需要实现复杂的避障功能。传统开发方式需要手动编写大量底层代码&#xff0c;调试起来特别耗时。不过这次尝试用InsCode(快马)平台的AI辅助功能&#xff0c;整个过程顺利了很多。 需求分析阶段 首先需要明确小车的核心功能&…...

驱动残留清理技术解析:Display Driver Uninstaller实战指南

驱动残留清理技术解析&#xff1a;Display Driver Uninstaller实战指南 【免费下载链接】display-drivers-uninstaller Display Driver Uninstaller (DDU) a driver removal utility / cleaner utility 项目地址: https://gitcode.com/gh_mirrors/di/display-drivers-uninsta…...

从羊肠小道到智能高速:HTTP1到HTTP3的演进之路

引言 计算机网络就像一张遍布全球的道路系统&#xff0c;服务器是一座座城市、村庄&#xff0c;客户端是穿梭其中的车辆&#xff0c;而HTTP协议&#xff0c;就是规范车辆通行、货物传递的交通规则。从HTTP1到HTTP3的演进&#xff0c;本质上就是这条“网络道路”的升级史——从泥…...

WarcraftHelper:魔兽争霸III游戏性能优化与兼容性解决方案完整指南

WarcraftHelper&#xff1a;魔兽争霸III游戏性能优化与兼容性解决方案完整指南 【免费下载链接】WarcraftHelper Warcraft III Helper , support 1.20e, 1.24e, 1.26a, 1.27a, 1.27b 项目地址: https://gitcode.com/gh_mirrors/wa/WarcraftHelper 还在为经典游戏《魔兽争…...

如何用baidupankey解决百度网盘提取码获取难题

如何用baidupankey解决百度网盘提取码获取难题 【免费下载链接】baidupankey 项目地址: https://gitcode.com/gh_mirrors/ba/baidupankey 引言&#xff1a;被提取码困住的日常 "又要找提取码&#xff1f;"小张盯着电脑屏幕上的百度网盘分享链接&#xff0c;…...

Zotero Citation插件开发指南:从环境适配到定制优化的全流程实践

Zotero Citation插件开发指南&#xff1a;从环境适配到定制优化的全流程实践 【免费下载链接】zotero-citation Make Zoteros citation in Word easier and clearer. 项目地址: https://gitcode.com/gh_mirrors/zo/zotero-citation 问题发现&#xff1a;学术写作中的引用…...

Qwen3-0.6B-FP8应用场景:开发者测试LLM应用前端UI兼容性的沙盒环境

Qwen3-0.6B-FP8应用场景&#xff1a;开发者测试LLM应用前端UI兼容性的沙盒环境 1. 引言&#xff1a;为什么需要一个轻量级的“测试沙盒”&#xff1f; 如果你正在开发一个基于大语言模型的应用&#xff0c;比如一个智能客服系统、一个文档助手&#xff0c;或者一个创意写作工…...

数字孪生通信层开发:C#实现OPC UA到Unity3D的实时数据映射(2026年工业级实战指南)

引言&#xff1a;通信层不是“锦上添花”&#xff0c;而是“数字孪生的血脉” 在2026年的工业数字孪生战场上&#xff0c;OPC UA到Unity3D的数据映射延迟是决定孪生体“活”与“死”的关键。IDC 2026年工业物联网报告显示&#xff1a;76%的数字孪生项目因通信层延迟>100ms失…...

nfc-list使用教程

nfc-list 是 Kali Linux 中基于 libnfc 库&#xff08;开源 NFC 开发框架&#xff09;的基础 NFC/RFID 设备检测工具&#xff0c;核心功能是扫描并列出当前连接的 NFC 读卡器设备&#xff0c;以及贴近读卡器的 NFC 卡片&#xff08;或标签&#xff09;的详细信息&#xff0c;包…...