Java设计模式——责任链模式与策略模式

ops/2025/2/11 12:03:06/

责任链模式与策略模式的区别

文章目录

  • 责任链模式与策略模式的区别
    • 定义与概念
    • 结构与实现
    • 应用场景
    • 总结

在软件开发中,设计模式是解决各种问题的有力工具。责任链模式和策略模式作为两种常见的设计模式,虽然都能在一定程度上提高代码的可维护性和可扩展性,但它们的应用场景和实现方式有很大的不同。以下是对这两种模式的详细分析和比较。

定义与概念

  • 责任链模式:使多个对象都有机会处理请求,从而避免请求的发送者和接收者之间的耦合关系。将这些对象连成一条链,并沿着这条链传递该请求,直到有一个对象处理它为止。
  • 策略模式:定义了一系列的算法,将每一个算法封装起来,并且使它们可以相互替换。策略模式让算法独立于使用它的客户而变化。

结构与实现

  • 责任链模式
    • 通常包含抽象处理者和具体处理者。抽象处理者定义了处理请求的抽象方法和设置下一个处理者的方法。具体处理者实现抽象处理者的方法,在处理请求时,先判断自己是否能处理,如果能则处理,否则将请求传递给下一个处理者。
    • 代码示例
java">// 抽象处理者
abstract class Handler {protected Handler nextHandler;public void setNextHandler(Handler nextHandler) {this.nextHandler = nextHandler;}public abstract void handleRequest(int request);
}// 具体处理者1
class ConcreteHandler1 extends Handler {@Overridepublic void handleRequest(int request) {if (request >= 0 && request < 10) {System.out.println("ConcreteHandler1处理请求:" + request);} else if (nextHandler!= null) {nextHandler.handleRequest(request);}}
}// 具体处理者2
class ConcreteHandler2 extends Handler {@Overridepublic void handleRequest(int request) {if (request >= 10 && request < 20) {System.out.println("ConcreteHandler2处理请求:" + request);} else if (nextHandler!= null) {nextHandler.handleRequest(request);}}
}// 客户端调用
public class Main {public static void main(String[] args) {Handler handler1 = new ConcreteHandler1();Handler handler2 = new ConcreteHandler2();handler1.setNextHandler(handler2);int[] requests = {5, 15, 25};for (int request : requests) {handler1.handleRequest(request);}}
}
  • 策略模式
    • 包含抽象策略类、具体策略类和环境类。抽象策略类定义了抽象的算法方法。具体策略类实现抽象策略类的算法方法,提供具体的算法实现。环境类持有一个抽象策略类的引用,通过调用抽象策略类的方法来执行具体的算法。
    • 代码示例
java">// 抽象策略
interface Strategy {int doOperation(int num1, int num2);
}// 具体策略1:加法策略
class AddStrategy implements Strategy {@Overridepublic int doOperation(int num1, int num2) {return num1 + num2;}
}// 具体策略2:减法策略
class SubtractStrategy implements Strategy {@Overridepublic int doOperation(int num1, int num2) {return num1 - num2;}
}// 环境类
class Context {private Strategy strategy;public Context(Strategy strategy) {this.strategy = strategy;}public int executeStrategy(int num1, int num2) {return strategy.doOperation(num1, num2);}
}// 客户端调用
public class Main {public static void main(String[] args) {Context addContext = new Context(new AddStrategy());Context subtractContext = new Context(new SubtractStrategy());System.out.println("10 + 5 = " + addContext.executeStrategy(10, 5));System.out.println("10 - 5 = " + subtractContext.executeStrategy(10, 5));}
}

应用场景

  • 责任链模式
    • 当有多个对象可以处理同一个请求,且处理顺序不确定,需要动态指定处理顺序时,适合使用责任链模式。比如,审批流程,不同级别的审批人构成责任链,根据具体的审批内容和金额等,由不同的审批人进行处理。
    • 日志处理系统,不同级别的日志(如DEBUG、INFO、WARN、ERROR)可以由不同的处理器来处理,形成一条责任链。
  • 策略模式
    • 当需要在不同的算法或行为之间进行切换,且这些算法或行为具有相同的目的但实现方式不同时,适合使用策略模式。比如,电商系统中的促销策略,有满减、折扣、赠品等不同的促销方式,可通过策略模式来实现。
    • 游戏中的角色行为,不同角色有不同的移动、攻击等行为,可将这些行为定义为不同的策略。

总结

比较维度责任链模式策略模式
目的将请求的发送和处理解耦,让多个对象都有机会处理请求将算法封装,使算法可相互替换,独立于使用它的客户
结构特点由多个处理者对象构成一条链,请求沿链传递由环境类持有抽象策略,通过组合不同的具体策略实现不同算法
行为特点请求会在责任链上传递,直到被处理或到达链尾根据选择的具体策略执行相应的算法,不存在请求传递
使用场景适用于处理流程不确定、有多个对象可处理同一请求的场景适用于有多种不同算法或行为,需要动态切换的场景
代码耦合度处理者之间存在一定耦合,通过链的关系连接策略与环境类之间耦合度较低,策略之间相对独立

责任链模式和策略模式虽然都是为了提高代码的可维护性和可扩展性,但它们解决的问题和应用场景不同。在实际开发中,需要根据具体的业务需求和系统设计来选择合适的设计模式


http://www.ppmy.cn/ops/157516.html

相关文章

【算法篇】贪心算法

目录 贪心算法 贪心算法实际应用 一&#xff0c;零钱找回问题 二&#xff0c;活动选择问题 三&#xff0c;分数背包问题 将数组和减半的最小操作次数 最大数 贪心算法 贪心算法&#xff0c;是一种在每一步选择中都采取当前状态下的最优策略&#xff0c;期望得到全局最优…

OpenAI Deep Research被huggingface 24小时复现开源了

自OpenAI发布Deep Research&#xff08;一种使用推理来综合大量在线信息并完成多步骤研究任务的AI Agent&#xff09;之后开源社区已经迎来一大波复现了&#xff0c;PaperAgent进行了梳理&#xff1a; 1.2k星 https://github.com/jina-ai/node-DeepResearch 825 https://gith…

MIT6.824 Lecture 2-RPC and Threads Lecture 3-GFS

Lecture 2-RPC and Threads Go语言在多线程、同步&#xff0c;还有很好用的RPC包 《Effective Go》 线程是实现并发的重要工具 在分布式系统里关注多线程的原因&#xff1a; I/O concurrencyParallelismConvenience Thread challenges 用锁解决race问题 Coordination channel…

记录 | WPF基础学习自定义按钮

目录 前言一、解析Button.TemplateBorder和TemplateBinding 二、代码提供更新时间 前言 参考文章&#xff1a; 参考视频&#xff1a;【WPF入门教程 Visual Studio 2022】WPF界面开发入门 自己的感想 这里涉及到Template模板和事件。主要干两件事&#xff1a;1、template中的重写…

vue中computed和watch的区别,以及适用场景

一、computed&#xff1a;通过属性计算而得来的属性 computed内部的函数在调用时不加()。computed是依赖vm中data的属性变化而变化的&#xff0c;也就是说&#xff0c;当data中的属性发生改变的时候&#xff0c;当前函数才会执行&#xff0c;data中的属性没有改变的时候&#…

防御综合实验

1、实验拓扑图 2、实验步骤 需求一&#xff1a;完成IP配置 FW OA Web DNS PC1 Client2 需求二&#xff1a;DHCP分配IP 需求三&#xff1a;配置安全区域 需求四&#xff1a;防火墙地址组信息 DMZ区域 TrustA TrustB 需求五&#xff1a;管理员 配…

【大模型】Ubuntu下安装ollama,DeepSseek-R1:32b的本地部署和运行

1 ollama 的安装与设置 ollama官网链接&#xff1a;https://ollama.com/ 在左上角的【Models】中展示了ollama支持的模型在正中间的【Download】中课可以下载支持平台中的安装包。   其安装和模型路径配置操作流程如下&#xff1a; ollama的安装 这里选择命令安装curl -fsSL …

使用Spring boot的@Transactional进行事务管理

文章目录 一、前置条件二、基本用法1. 在方法上添加注解2. 在类上添加注解 三、核心配置参数1. 传播行为&#xff08;Propagation&#xff09;2. 隔离级别&#xff08;Isolation&#xff09;3. 超时时间&#xff08;Timeout&#xff09;4. 只读模式&#xff08;readOnly&#x…