设计模式之责任链模式:原理、实现与应用

devtools/2025/3/29 7:28:35/
引言

责任链模式(Chain of Responsibility Pattern)是一种行为型设计模式,它允许多个对象有机会处理请求,从而避免请求的发送者与接收者之间的耦合。责任链模式通过将多个处理对象连接成一条链,使得请求沿着链传递,直到有对象处理它为止。本文将深入探讨责任链模式的原理、实现方式以及实际应用场景,帮助你更好地理解和使用这一设计模式


1. 责任链模式的核心概念

1.1 什么是责任链模式

责任链模式是一种行为型设计模式,它允许多个对象有机会处理请求,从而避免请求的发送者与接收者之间的耦合。责任链模式通过将多个处理对象连接成一条链,使得请求沿着链传递,直到有对象处理它为止。

1.2 责任链模式的应用场景
  • 多级审批:如请假审批、报销审批等。

  • 事件处理:如GUI事件处理、异常处理等。

  • 过滤器链:如Web请求过滤器、日志过滤器等。


2. 责任链模式的实现方式

2.1 基本结构

责任链模式通常包含以下几个角色:

  • 处理者接口(Handler):定义处理请求的接口,并持有下一个处理者的引用。

  • 具体处理者(Concrete Handler):实现处理者接口,处理请求或将请求传递给下一个处理者。

  • 客户端(Client):创建责任链,并向链中的第一个处理者发送请求。

2.2 代码示例
// 处理者接口
public interface Handler {void setNext(Handler next);void handleRequest(Request request);
}// 具体处理者A
public class ConcreteHandlerA implements Handler {private Handler next;@Overridepublic void setNext(Handler next) {this.next = next;}@Overridepublic void handleRequest(Request request) {if (request.getType().equals("TypeA")) {System.out.println("ConcreteHandlerA handled the request");} else if (next != null) {next.handleRequest(request);}}
}// 具体处理者B
public class ConcreteHandlerB implements Handler {private Handler next;@Overridepublic void setNext(Handler next) {this.next = next;}@Overridepublic void handleRequest(Request request) {if (request.getType().equals("TypeB")) {System.out.println("ConcreteHandlerB handled the request");} else if (next != null) {next.handleRequest(request);}}
}// 请求类
public class Request {private String type;public Request(String type) {this.type = type;}public String getType() {return type;}
}// 客户端代码
public class Client {public static void main(String[] args) {Handler handlerA = new ConcreteHandlerA();Handler handlerB = new ConcreteHandlerB();handlerA.setNext(handlerB);Request request1 = new Request("TypeA");handlerA.handleRequest(request1);Request request2 = new Request("TypeB");handlerA.handleRequest(request2);Request request3 = new Request("TypeC");handlerA.handleRequest(request3);}
}

3. 责任链模式的最佳实践

3.1 动态构建责任链
  • 灵活性:通过动态构建责任链,可以根据需要调整处理者的顺序和数量。

  • 可扩展性:通过添加新的处理者,可以轻松扩展责任链的功能。

3.2 避免循环引用
  • 循环引用:在构建责任链时,避免处理者之间形成循环引用,导致请求无限循环。

3.3 遵循单一职责原则
  • 单一职责:每个处理者只负责处理特定类型的请求,保持职责单一。

  • 高内聚低耦合责任链模式使得系统更加高内聚低耦合。


4. 责任链模式的实际应用

4.1 多级审批

在多级审批中,责任链模式用于处理不同级别的审批请求。

// 处理者接口
public interface Approver {void setNext(Approver next);void approve(int amount);
}// 具体处理者
public class Manager implements Approver {private Approver next;@Overridepublic void setNext(Approver next) {this.next = next;}@Overridepublic void approve(int amount) {if (amount <= 1000) {System.out.println("Manager approved the request");} else if (next != null) {next.approve(amount);}}
}public class Director implements Approver {private Approver next;@Overridepublic void setNext(Approver next) {this.next = next;}@Overridepublic void approve(int amount) {if (amount <= 5000) {System.out.println("Director approved the request");} else if (next != null) {next.approve(amount);}}
}public class CEO implements Approver {@Overridepublic void setNext(Approver next) {// CEO is the final approver}@Overridepublic void approve(int amount) {System.out.println("CEO approved the request");}
}// 客户端代码
public class Client {public static void main(String[] args) {Approver manager = new Manager();Approver director = new Director();Approver ceo = new CEO();manager.setNext(director);director.setNext(ceo);manager.approve(500);manager.approve(2000);manager.approve(10000);}
}
4.2 事件处理

在事件处理中,责任链模式用于处理不同类型的事件。

// 处理者接口
public interface EventHandler {void setNext(EventHandler next);void handle(Event event);
}// 具体处理者
public class MouseEventHandler implements EventHandler {private EventHandler next;@Overridepublic void setNext(EventHandler next) {this.next = next;}@Overridepublic void handle(Event event) {if (event.getType().equals("MouseEvent")) {System.out.println("MouseEventHandler handled the event");} else if (next != null) {next.handle(event);}}
}public class KeyboardEventHandler implements EventHandler {private EventHandler next;@Overridepublic void setNext(EventHandler next) {this.next = next;}@Overridepublic void handle(Event event) {if (event.getType().equals("KeyboardEvent")) {System.out.println("KeyboardEventHandler handled the event");} else if (next != null) {next.handle(event);}}
}// 事件类
public class Event {private String type;public Event(String type) {this.type = type;}public String getType() {return type;}
}// 客户端代码
public class Client {public static void main(String[] args) {EventHandler mouseHandler = new MouseEventHandler();EventHandler keyboardHandler = new KeyboardEventHandler();mouseHandler.setNext(keyboardHandler);Event mouseEvent = new Event("MouseEvent");mouseHandler.handle(mouseEvent);Event keyboardEvent = new Event("KeyboardEvent");mouseHandler.handle(keyboardEvent);Event unknownEvent = new Event("UnknownEvent");mouseHandler.handle(unknownEvent);}
}
4.3 过滤器链

在过滤器链中,责任链模式用于处理Web请求或日志记录。

// 处理者接口
public interface Filter {void setNext(Filter next);void doFilter(Request request);
}// 具体处理者
public class AuthenticationFilter implements Filter {private Filter next;@Overridepublic void setNext(Filter next) {this.next = next;}@Overridepublic void doFilter(Request request) {if (request.getType().equals("Authentication")) {System.out.println("AuthenticationFilter handled the request");} else if (next != null) {next.doFilter(request);}}
}public class LoggingFilter implements Filter {private Filter next;@Overridepublic void setNext(Filter next) {this.next = next;}@Overridepublic void doFilter(Request request) {if (request.getType().equals("Logging")) {System.out.println("LoggingFilter handled the request");} else if (next != null) {next.doFilter(request);}}
}// 请求类
public class Request {private String type;public Request(String type) {this.type = type;}public String getType() {return type;}
}// 客户端代码
public class Client {public static void main(String[] args) {Filter authenticationFilter = new AuthenticationFilter();Filter loggingFilter = new LoggingFilter();authenticationFilter.setNext(loggingFilter);Request authRequest = new Request("Authentication");authenticationFilter.doFilter(authRequest);Request logRequest = new Request("Logging");authenticationFilter.doFilter(logRequest);Request unknownRequest = new Request("Unknown");authenticationFilter.doFilter(unknownRequest);}
}

5. 责任链模式的优缺点

5.1 优点
  • 解耦责任链模式将请求的发送者与接收者解耦,使得请求的发送者无需知道具体的处理者。

  • 灵活性:通过动态构建责任链,可以根据需要调整处理者的顺序和数量。

  • 可扩展性:通过添加新的处理者,可以轻松扩展责任链的功能。

5.2 缺点
  • 性能问题:如果责任链过长,可能会导致性能问题。

  • 请求未被处理:如果请求未被任何处理者处理,可能会导致请求丢失。


结语

责任链模式设计模式中用于处理请求的经典模式之一,适用于需要将请求的发送者与接收者解耦的场景。通过掌握责任链模式的原理、实现方式以及最佳实践,你可以在实际开发中更好地应用这一模式。希望本文能为你的设计模式学习之旅提供一些实用的指导!


如果你有具体的需求或想要深入探讨某个主题,请告诉我,我可以进一步调整内容!


http://www.ppmy.cn/devtools/170628.html

相关文章

vim的一般操作(分屏操作) 和 Makefile 和 gdb

目录 一. vim的基本概念 二. vim基础操作 2.1 插入模式 aio 2.2 [插入模式]切换至[正常模式] Esc 2.3[正常模式]切换至[末行模式] shift ; 2.4 替换模式 Shift R 2.5 视图&#xff08;可视&#xff09;模式 (可以快速 删除//注释 或者 增加//注释) ctrl v 三&…

Qt下集成大华网络相机SDK示例开发

文章目录 前言一、下载并集成大华网络相机SDK二、示例实现功能三、示例完整代码四、下载链接总结 前言 近期在Qt环境下进行大华网络相机的使用&#xff0c;发现官网下载的SDK中提供的示例没有Qt的demo&#xff0c;通过学习其提供的MFC示例代码&#xff0c;我在这里也实现了一个…

Elasticsearch 在航空行业:数据管理的游戏规则改变者

作者&#xff1a;来自 Elastic Adam La Roche 数字化客户体验不再是奢侈品&#xff0c;而是欧洲航空公司必不可少的需求。它推动了客户满意度&#xff0c;提升了运营效率&#xff0c;并创造了可持续的竞争优势。随着行业的不断发展&#xff0c;优先投资前沿数字技术和平台的航空…

prometheus 添加alertmanager添加dingtalk机器人告警

1、dingtalk创建机器人,目前我们采用加白名单的方式校验 2、定位到如下图 test结果如下

美团Leaf分布式ID生成器使用教程:号段模式与Snowflake模式详解

引言 在分布式系统中&#xff0c;生成全局唯一ID是核心需求之一。美团开源的Leaf提供了两种分布式ID生成方案&#xff1a;号段模式&#xff08;高可用、依赖数据库&#xff09;和Snowflake模式&#xff08;高性能、去中心化&#xff09;。本文将手把手教你如何配置和使用这两种…

点亮STM32最小系统板LED灯

对于如何点亮板载LED灯只需要掌握如何初始化GPIO引脚&#xff0c;并改变GPIO引脚的电平即可实现点亮或者熄灭LED。 Led_INFO led_info {0}; led_info 是一个结构体变量&#xff0c;类型为 Led_INFO&#xff0c;用于存储LED的状态信息。这里初始化为 {0}&#xff0c;表示所有成…

【css酷炫效果】纯CSS实现球形阴影效果

【css酷炫效果】纯CSS实现球形阴影效果 缘创作背景html结构css样式完整代码基础版进阶版(动态版) 效果图 想直接拿走的老板&#xff0c;链接放在这里&#xff1a;上传后更新 缘 创作随缘&#xff0c;不定时更新。 创作背景 刚看到csdn出活动了&#xff0c;赶时间&#xff0…

GitHub 超火的开源终端工具——Warp

Warp 作为近年来 GitHub 上备受瞩目的开源终端工具&#xff0c;以其智能化、高性能和协作能力重新定义了命令行操作体验。以下从多个维度深入解析其核心特性、技术架构、用户评价及生态影响力&#xff1a; 一、背景与核心团队 Warp 由前 GitHub CTO Jason Warner 和 Google 前…