Java设计模式之责任链模式

1、责任链模式的定义:

责任链模式(Iterator Pattern)是一种行为型设计模式,使多个对象都有机会处理同一个请求,将这些对象连成一条链,并沿着这条链传递该请求,直到有一个对象处理它为止。

2、责任链模式的角色:

抽象处理器AbstractHandler:是一个接口或抽象类,定义要处理的方法。

具体处理器Handler:对抽象处理器的具体实现,重写处理方法,调用处理器链的方法。

处理器链HandlerChain:通过数组或链表组织各个具体的处理器形成一个处理器链,提供添加处理器的方法,并调用处理器的处理方法。

3、责任链模式的使用场景

1.多个对象可以处理同一个请求,但具体由哪个对象处理则在运行时动态决定。

2.在请求处理器个数未知的情况下,或者请求处理器可动态配置的情况下,可以使用责任链模式。

4、使用责任链模式的样例代码一

需求:当用户发起请求时,通过多个过滤器对请求数据进行过滤

抽象处理器:

package com.design.mode.responsibilityChain.responsibility01;

/**
 * @Author: 倚天照海
 * @Description: 抽象处理器
 */
public interface MyFilter {

    boolean doFilter(MyRequest request, MyResponse response, MyFilterChain chain);

}

具体处理器:

package com.design.mode.responsibilityChain.responsibility01;

/**
 * @Author: 倚天照海
 * @Description: 一个具体处理器,登录过滤器
 */
public class LoginFilter implements MyFilter {

    @Override
    public boolean doFilter(MyRequest request, MyResponse response, MyFilterChain chain) {
        String reqMsg = request.getReqMsg();
        if (!reqMsg.contains("username") || !reqMsg.contains("password")){
            System.out.println("登录失败,请重新登录");
            return false;
        }
        //chain.doFilter(request,response,chain);
        String resMsg = response.getResMsg();
        resMsg += "--登录过滤器返回响应消息";
        response.setResMsg(resMsg);
        return true;
    }
}



package com.design.mode.responsibilityChain.responsibility01;

/**
 * @Author: 倚天照海
 * @Description: 一个具体处理器,业务过滤器
 */
public class BusinessFilter implements MyFilter {

    @Override
    public boolean doFilter(MyRequest request, MyResponse response, MyFilterChain chain) {
        String reqMsg = request.getReqMsg();
        if (!reqMsg.contains("/filter")){
            System.out.println("请求的接口路径不存在");
            return false;
        }
        //chain.doFilter(request,response,chain);
        String resMsg = response.getResMsg();
        resMsg += "--业务逻辑处理完返回响应消息";
        response.setResMsg(resMsg);
        return true;
    }
}

处理器链:

package com.design.mode.responsibilityChain.responsibility01;

import java.util.ArrayList;
import java.util.List;

/**
 * @Author: 倚天照海
 * @Description: 责任链模式,模拟javax.servlet.Filter和FilterChain
 */
public class MyFilterChain {

    //private int index = 0;

    private List<MyFilter> filterList = new ArrayList<MyFilter>();

    /**
     * 将处理器添加到处理器链中
     */
    public MyFilterChain addFilter(MyFilter filter){
        filterList.add(filter);
        return this;
    }

    /**
     * 使用这种方式判断,第三个参数chain可以不要了
     */
    public void doFilter(MyRequest request, MyResponse response, MyFilterChain chain){
        for (MyFilter filter : filterList){
            //第三个参数chain可以不要了
            if (!filter.doFilter(request, response, chain)){
                break;
            }
        }
    }

    /*public void doFilter(MyRequest request, MyResponse response, MyFilterChain chain){
        if (index == filterList.size()){
            return;
        }
        MyFilter filter = filterList.get(index);
        index++;
        //调用处理器的方法
        filter.doFilter(request, response, chain);
    }*/

}

其中用到的实体类:

package com.design.mode.responsibilityChain.responsibility01;

/**
 * @Author: 倚天照海
 * @Description:
 */
public class MyRequest {

    private String reqMsg;

    public String getReqMsg() {
        return reqMsg;
    }

    public void setReqMsg(String reqMsg) {
        this.reqMsg = reqMsg;
    }
}


package com.design.mode.responsibilityChain.responsibility01;

/**
 * @Author: 倚天照海
 * @Description:
 */
public class MyResponse {

    private String resMsg;

    public String getResMsg() {
        return resMsg;
    }

    public void setResMsg(String resMsg) {
        this.resMsg = resMsg;
    }
}

测试类:

package com.design.mode.responsibilityChain.responsibility01;

/**
 * @Author: 倚天照海
 */
public class RespChainTest01 {

    public static void main(String[] args) {
        String reqMsg = "{username:andy,password:123456,url:\"http://ip:port/filter\"}";
        MyRequest request = new MyRequest();
        request.setReqMsg(reqMsg);
        MyResponse response = new MyResponse();
        //创建具体的处理器和处理器链
        MyFilterChain chain = new MyFilterChain();
        MyFilter loginFilter = new LoginFilter();
        MyFilter businessFilter = new BusinessFilter();
        //将处理器添加到处理器链中
        chain.addFilter(loginFilter).addFilter(businessFilter);
        chain.doFilter(request,response,chain);
        String resMsg = response.getResMsg();
        System.out.println("得到响应结果=======" + resMsg);
    }

}

5、使用责任链模式的样例代码二

需求:根据员工请假天数不同,组长、主管、经理分别审批

实体类:

package com.design.mode.responsibilityChain.responsibility02;

/**
 * @Author: 倚天照海
 * @Description: 请假请求实体类
 */
public class LeaveRequest {

    private Integer days;

    private String reason;

    public LeaveRequest() {
    }

    public Integer getDays() {
        return days;
    }

    public void setDays(Integer days) {
        this.days = days;
    }

    public String getReason() {
        return reason;
    }

    public void setReason(String reason) {
        this.reason = reason;
    }

    @Override
    public String toString() {
        return "Leave{" +
                "days=" + days +
                ", reason='" + reason + '\'' +
                '}';
    }
}



package com.design.mode.responsibilityChain.responsibility02;

/**
 * @Author: 倚天照海
 * @Description: 请假结果实体类
 */
public class Result {
    /**
     * 是否批准
     */
    private boolean isRatify;

    private String info;

    public boolean isRatify() {
        return isRatify;
    }

    public void setRatify(boolean ratify) {
        isRatify = ratify;
    }

    public String getInfo() {
        return info;
    }

    public void setInfo(String info) {
        this.info = info;
    }

    @Override
    public String toString() {
        return "Result{" +
                "isRatify=" + isRatify +
                ", info='" + info + '\'' +
                '}';
    }
}

抽象处理器:

package com.design.mode.responsibilityChain.responsibility02;

/**
 * @Author: 倚天照海
 * @Description: 批准接口,抽象处理器
 */
public interface Ratify {

    Result handle(LeaveRequest request, Result result, MyChain chain);

}

三个具体处理器:

package com.design.mode.responsibilityChain.responsibility02;

/**
 * @Author: 倚天照海
 * @Description: 一个具体处理器,组长实体类,只能批准两天内的假期
 */
public class GroupLeader implements Ratify {

    @Override
    public Result handle(LeaveRequest request, Result result, MyChain chain) {
        Integer days = request.getDays();
        if (days <= 2){
            result.setRatify(true);
            result.setInfo("组长同意,早去早回。");
        } else {
            //result.setRatify(true);
            chain.doFilter(request,result,chain);
        }
        return result;
    }
}


package com.design.mode.responsibilityChain.responsibility02;

/**
 * @Author: 倚天照海
 * @Description: 一个具体处理器,部门主管,可以批准4天内的假期
 */
public class DepartmentHead implements Ratify {

    @Override
    public Result handle(LeaveRequest request, Result result, MyChain chain) {
        Integer days = request.getDays();
        if (days <= 4){
            result.setRatify(true);
            result.setInfo("主管同意,路上注意安全。");
        } else {
            //result.setRatify(true);
            chain.doFilter(request,result,chain);
        }
        return result;
    }
}


package com.design.mode.responsibilityChain.responsibility02;

/**
 * @Author: 倚天照海
 * @Description: 一个具体处理器,部门经理,可以批准7天内的假期,超过7天不批准
 */
public class DepartmentManager implements Ratify {

    @Override
    public Result handle(LeaveRequest request, Result result, MyChain chain) {
        Integer days = request.getDays();
        if (days <= 7){
            result.setRatify(true);
            result.setInfo("经理同意,回去安心办事。");
        } else {
            result.setRatify(false);
            result.setInfo("经理不同意,时间太久。");
            chain.doFilter(request,result,chain);
        }
        return result;
    }
}

处理器链:

package com.design.mode.responsibilityChain.responsibility02;

import java.util.ArrayList;
import java.util.List;

/**
 * @Author: 倚天照海
 * @Description: 处理器链,责任链模式
 */
public class MyChain {

    private int index = 0;

    private List<Ratify> filterList = new ArrayList<Ratify>();

    public MyChain addFilter(Ratify ratify){
        filterList.add(ratify);
        return this;
    }

    public void doFilter(LeaveRequest request, Result result, MyChain chain){
        if (index == filterList.size()){
            return;
        }
        Ratify ratify = filterList.get(index);
        index++;
        ratify.handle(request, result, chain);
    }

}

测试类:

package com.design.mode.responsibilityChain.responsibility02;

/**
 * @Author: 倚天照海
 * @Description:
 */
public class RespChainTest02 {

    public static void main(String[] args) {
        LeaveRequest request = new LeaveRequest();
        request.setDays(3);
        Result result = new Result();

        MyChain chain = new MyChain();
        Ratify leader = new GroupLeader();
        Ratify head = new DepartmentHead();
        Ratify manager = new DepartmentManager();
        chain.addFilter(leader).addFilter(head).addFilter(manager);
        chain.doFilter(request,result,chain);
        System.out.println("请假结果======" + result);
    }

}

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

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

相关文章

web安全测试渗透案例知识点总结(下)——小白入狱

目录 [TOC](目录)一、更多详细的实际案例教程案例1&#xff1a;文件上传漏洞利用案例2&#xff1a;目录遍历&#xff08;Path Traversal&#xff09;漏洞检测案例3&#xff1a;暴力破解登录密码案例4&#xff1a;命令注入漏洞案例5&#xff1a;身份认证绕过&#xff08;Passwor…

.NET 8 中 Entity Framework Core 的使用

本文代码&#xff1a;https://download.csdn.net/download/hefeng_aspnet/89935738 概述 Entity Framework Core (EF Core) 已成为 .NET 开发中数据访问的基石工具&#xff0c;为开发人员提供了强大而多功能的解决方案。随着 .NET 8 和 C# 10 中引入的改进&#xff0c;开发人…

后端java——如何为你的网页设置一个验证码

本文通过HUTOOL实现&#xff1a;Hutool参考文档Hutool&#xff0c;Java工具集https://hutool.cn/docs/#/ 1、工具的准备 如果我们通过hutool来实现这个功能&#xff0c;我们需要提前安装hutool的jar包。 下载地址&#xff1a;Central Repository: cn/hutool/hutool-all/5.8.…

Java面试经典 150 题.P189. 轮转数组(006)

本题来自&#xff1a;力扣-面试经典 150 题 面试经典 150 题 - 学习计划 - 力扣&#xff08;LeetCode&#xff09;全球极客挚爱的技术成长平台https://leetcode.cn/studyplan/top-interview-150/ 题解&#xff1a; class Solution {public void rotate(int[] nums, int k) {…

Cesium基础-(Entity)-(ellipsoid)

里边包含Vue、React框架代码详细步骤、以及代码详细解释 7、ellipsoid 球体与椭球体 Ellipsoid(椭球体)是 Cesium 中用来表示地球或其他天体形状的几何对象。在三维空间中,椭球体是一个被拉伸或压缩的球体,它由三个半径定义:沿着 x、y 和 z 轴的半径。这些半径确定了椭球体…

nvm详解

本文借鉴转载于 nvm文档手册 文章目录 1.nvm是什么&#xff1f;2.nvm安装2.1 window上安装下载链接安装步骤 2.2 Mac上安装使用homebrew 安装 nvm 3.nvm使用指令 1.nvm是什么&#xff1f; nvm&#xff08;Node Version Manager&#xff09;是一个用于管理和切换不同版本 Node.…

【辽宁】《辽宁省省级政务信息化建设项目预算支出标准规定(试行)》(辽财预〔2021〕54号)-省市费用标准解读系列04

《辽宁省省级政务信息化建设项目预算支出标准规定&#xff08;试行&#xff09;》&#xff08;辽财预〔2021〕54号&#xff09;是由辽宁省财政厅和辽宁省信息中心于2021年发布应用的信息化建设项目预算支出标准。我司基于专业第三方信息化项目造价机构角度&#xff0c;从标准创…

基于vue3和elementPlus的el-tree组件,实现树结构穿梭框,支持数据回显和懒加载

一、功能 功能描述 数据双向穿梭&#xff1a;支持从左侧向右侧转移数据&#xff0c;以及从右侧向左侧转移数据。懒加载支持&#xff1a;支持懒加载数据&#xff0c;适用于大数据量的情况。多种展示形式&#xff1a;右侧列表支持以树形结构或列表形式展示。全选与反选&#xf…

Python数据分析案例61——信贷风控评分卡模型(A卡)(scorecardpy 全面解析)

案例背景 虽然在效果上&#xff0c;传统的逻辑回归模型通常不如现代的机器学习模型&#xff0c;但在风控领域&#xff0c;解释性至关重要。逻辑回归的解释性是这些“黑箱”模型所无法比拟的&#xff0c;因此&#xff0c;研究传统的评分卡模型依然是有意义的。 传统的评分卡模型…

Canvas 教程(一)

目录 一、初体验 二、通过js的方式创建canvas 三、为什么推荐属性的方式设置canvas的宽高&#xff1f; 四、常见画笔API 4.1 画直线 &#x1f536; 步骤 &#x1fae2; 小练习 4.2 线条的样式 4.2.1 线条的宽度设置 &#x1f536; API 4.2.2 线条的颜色设置 &#…

[CISCN 2019华北]PWN1-好久不见7

Partial RELRO 表示部分 RELRO 保护已启用。在这种情况下&#xff0c;只有某些部分&#xff08;如 GOT 中的只读部分&#xff09;是只读的。 NX enabled 表示这个二进制文件启用了 NX 保护&#xff0c;数据段是不可执行的。这可以防止某些类型的代码注入攻击。 这里是ida识别…

Leetcode 64. 最小路径和 动态规划+空间优化

原题链接&#xff1a;Leetcode 64. 最小路径和 二维数据 class Solution { public:int minPathSum(vector<vector<int>>& grid) {int m grid.size();int n grid[0].size();int dp[m][n];dp[0][0] grid[0][0];for (int j 1; j < n; j)dp[0][j] dp[0][…

教你一个免费把PDF产品宣传册转化为翻页电子产品宣传册的方法

在这个数字化时代&#xff0c;电子宣传册已经成为企业推广产品的重要手段。相比于传统的纸质宣传册&#xff0c;电子宣传册具有更高的互动性和传播效率。那么&#xff0c;如何将现有的PDF产品宣传册转化为具有翻页效果的电子宣传册呢&#xff1f;本文将为您详细介绍一种免费的方…

大数阶乘求末尾0的个数

题目&#xff1a;求123…n所得数的末尾有多少个0&#xff1f;n由键盘输入&#xff0c;且1000<n<10000。 答&#xff1a;思路1&#xff1a;考虑末尾0的来源。阶乘结果末尾的零是由于因数10的存在&#xff0c;10分解质因数&#xff1a;25。在阶乘的计算中&#xff0c;偶数&…

2024最新的开源博客系统:vue3.x+SpringBoot 3.x 前后端分离

本文转载自&#xff1a;https://fangcaicoding.cn/article/54 大家好&#xff01;我是方才&#xff0c;目前是8人后端研发团队的负责人&#xff0c;拥有6年后端经验&3年团队管理经验&#xff0c;截止目前面试过近200位候选人&#xff0c;主导过单表上10亿、累计上100亿数据…

鸿蒙生态下开发挑战-鸿蒙低代码开发工具展望及优势

鸿蒙生态下开发挑战 在鸿蒙生态下开发时&#xff0c;开发者可能会遇到多方面的挑战&#xff0c;这些挑战主要涉及开发工具、技术难度、生态竞争以及市场定位等方面。以下是对这些挑战的详细分析&#xff1a; 一、开发工具不完善 尽管鸿蒙系统的开发工具DevEco Studio在逐步完…

JavaScript的迭代器和生成器

1. 迭代器Iterator 1. 基本概念 JavaScript 表示集合的对象大致有Object&#xff0c;Array&#xff0c;Map&#xff0c;Set四种&#xff0c;并且这四种类型的数据之间可以相互以成员嵌套&#xff08;如Array的成员可以是Object&#xff0c;而Map又可以嵌入Object的成员中&am…

深度学习常用开源数据集介绍【持续更新】

DIV2K 介绍&#xff1a;DIV2K是一个专为 图像超分辨率&#xff08;SR&#xff09; 任务设计的高质量数据集&#xff0c;广泛应用于计算机视觉领域的研究和开发。它包含800张高分辨率&#xff08;HR&#xff09;训练图像和100张高分辨率验证图像&#xff0c;每张图像都具有极高…

Pinia-状态管理

Pinia-状态管理 特点&#xff1a; 1. 轻量和模块化 Pinia 是一个轻量级的状态管理库&#xff0c;支持模块化管理&#xff0c;即可以将应用的状态分成多个 store 以实现更好的组织。使用 Pinia&#xff0c;可以定义多个 store&#xff0c;每个 store 都是一个独立的模块&#x…

向量模型Jina Embedding: 从v1到v3论文笔记

文章目录 Jina Embedding: 从v1到v3Jina Embedding v1数据集准备训练过程 Jina Embedding v2预训练修改版BERT在文本对上微调在Hard Negatives上微调 Jina Embedding v2 双语言预训练修改版BERT在文本对上微调用多任务目标微调 Jina Embedding v3预训练在文本对上微调训练任务相…