设计模式之责任链模式

文章目录

责任链模式(Chain of Responsibility)

问题

在某些情况下,一个请求需要在多个对象之间传递,每个对象都可能处理该请求或将其传递给下一个对象。在这种情况下,需要避免将发送者与接收者之间的耦合,以及确定请求的处理方式。问题在于如何设计一个机制,使得多个对象都有机会处理请求,而且可以根据需要动态地改变它们之间的顺序和职责。

解决方案

责任链模式提供了一种通过一系列处理对象来处理请求的方法。每个处理对象都包含一个对下一个处理对象的引用,形成一个链式结构。当一个请求到达时,它首先被传递给链中的第一个处理对象,如果该对象不能处理该请求,它会将请求传递给下一个处理对象,依此类推,直到找到能够处理请求的对象为止。

责任链模式的解决方案包括以下关键点:

  • 定义一个抽象处理者(Handler)类,该类包含一个对下一个处理者的引用,并声明一个处理请求的方法。
  • 具体的处理者类继承自抽象处理者类,实现处理请求的方法。在该方法中,处理者可以决定是否处理请求,如果不能处理,则将请求传递给下一个处理者。
  • 客户端创建一个处理链,将处理者按照一定的顺序连接起来。

效果:

责任链模式的应用可以带来多个效果:

  • 降低耦合度:发送者不需要知道哪个对象会处理请求,只需将请求发送到链的起始点
  • 灵活性:可以根据需要动态地改变处理链中处理者的顺序,以及每个处理者的职责。
  • 可扩展性:可以很容易地添加新的处理者,而不会影响现有代码。
  • 可维护性:每个处理者关注单一的责任,使得代码更易于理解和维护。

然而,责任链模式也有一些潜在的限制,比如可能导致请求无法被处理或者处理链太长而导致性能问题。因此,在使用责任链模式时需要谨慎权衡权衡利弊。

总之,责任链模式是一种有助于将请求与处理者解耦,并支持动态调整处理顺序和职责的设计模式。

代码实例

java 复制代码
// 首先,我们需要创建一个表示请求的类 ReimbursementRequest
public class ReimbursementRequest {
    private double amount;
    private String description;

    public ReimbursementRequest(double amount, String description) {
        this.amount = amount;
        this.description = description;
    }

    public double getAmount() {
        return amount;
    }

    public String getDescription() {
        return description;
    }
}
// 然后,创建一个抽象处理者类 ReimbursementHandler
public abstract class ReimbursementHandler {
    protected ReimbursementHandler successor;

    public void setSuccessor(ReimbursementHandler successor) {
        this.successor = successor;
    }

    public abstract void handleRequest(ReimbursementRequest request);
}

// 接下来,实现具体的处理者类:经理、部门主管和财务部门处理者。
public class ManagerHandler extends ReimbursementHandler {
    @Override
    public void handleRequest(ReimbursementRequest request) {
        if (request.getAmount() <= 1000) {
            System.out.println("经理处理报销请求:" + request.getDescription());
        } else if (successor != null) {
            successor.handleRequest(request);
        }
    }
}

public class DepartmentHeadHandler extends ReimbursementHandler {
    @Override
    public void handleRequest(ReimbursementRequest request) {
        if (request.getAmount() <= 5000) {
            System.out.println("部门主管处理报销请求:" + request.getDescription());
        } else if (successor != null) {
            successor.handleRequest(request);
        }
    }
}

public class FinanceHandler extends ReimbursementHandler {
    @Override
    public void handleRequest(ReimbursementRequest request) {
        System.out.println("财务部门处理报销请求:" + request.getDescription());
    }
}

// 在这个示例中,报销请求会依次被经理、部门主管和财务部门处理。根据报销金额的不同,请求会被传递到适当的处理者。
public class Main {
    public static void main(String[] args) {
        ReimbursementHandler manager = new ManagerHandler();
        ReimbursementHandler departmentHead = new DepartmentHeadHandler();
        ReimbursementHandler finance = new FinanceHandler();

        manager.setSuccessor(departmentHead);
        departmentHead.setSuccessor(finance);

        ReimbursementRequest request1 = new ReimbursementRequest(800, "购买办公用品");
        ReimbursementRequest request2 = new ReimbursementRequest(3000, "参加培训");
        ReimbursementRequest request3 = new ReimbursementRequest(10000, "举办团建活动");

        manager.handleRequest(request1);
        manager.handleRequest(request2);
        manager.handleRequest(request3);
    }
}

本人水平有限,有错的地方还请批评指正。

什么是精神内耗?

简单地说,就是心理戏太多,自己消耗自己。

所谓:

言未出,结局已演千百遍;

身未动,心中已过万重山;

行未果,假想灾难愁不展;

事已闭,过往仍在脑中演。

相关推荐
沐森8 小时前
在实战中运用泛型和动态trait(特质)
设计模式
lomocode9 小时前
改一个需求动 23 处代码?你可能踩进了这个坑
后端·设计模式
喷火龙8号10 小时前
JWT 认证方案深度对比:单 Token 扩展刷新 vs 双 Token 验证
后端·设计模式·架构
fakerth1 天前
【OpenHarmony】设计模式模块详解
c++·单例模式·设计模式·openharmony
alibli1 天前
一文学会设计模式之创建型模式及最佳实现
c++·设计模式
1024肥宅1 天前
前端常用模式:提升代码质量的四大核心模式
前端·javascript·设计模式
郝学胜-神的一滴1 天前
设计模式依赖于多态特性
java·开发语言·c++·python·程序人生·设计模式·软件工程
帅次1 天前
系统分析师:软件需求工程的软件需求概述、需求获取、需求分析
设计模式·重构·软件工程·团队开发·软件构建·需求分析·规格说明书
EXtreme352 天前
【数据结构】算法艺术:如何用两个栈(LIFO)优雅地模拟队列(FIFO)?
c语言·数据结构·算法·设计模式·栈与队列·摊还分析·算法艺术
1024肥宅2 天前
JavaScript常用设计模式完整指南
前端·javascript·设计模式