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

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 {
    @Override
    public 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 {
    @Override
    public 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);
        }
    }
}
  • 策略模式
    • 包含抽象策略类、具体策略类和环境类。抽象策略类定义了抽象的算法方法。具体策略类实现抽象策略类的算法方法,提供具体的算法实现。环境类持有一个抽象策略类的引用,通过调用抽象策略类的方法来执行具体的算法。
    • 代码示例
// 抽象策略
interface Strategy {
    int doOperation(int num1, int num2);
}

// 具体策略1:加法策略
class AddStrategy implements Strategy {
    @Override
    public int doOperation(int num1, int num2) {
        return num1 + num2;
    }
}

// 具体策略2:减法策略
class SubtractStrategy implements Strategy {
    @Override
    public 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.kler.cn/a/545516.html

相关文章:

  • 可编程网卡芯片在京东云网络的应用实践【BGW边界网关篇】
  • 如何用CSS解决边距合并问题?
  • SANS 网络安全 网络安全三件套
  • MongoDB 入门操作指南
  • C++,STL容器适配器,stack:栈深入解析
  • 【网络安全 | 漏洞挖掘】跨子域账户合并导致的账户劫持与删除
  • Python + WhisperX:解锁语音识别的高效新姿势
  • 基于MATLAB的沥青试样孔隙率自动分析——原理详解与代码实现
  • 初识Linux · 重定向和缓冲区(续)
  • Go 语言常用的结构体标签解析
  • 基于 GEE 计算研究区年均地表温度数据
  • Unity状态机的实现方法一
  • 【Elasticsearch】字符过滤器Character Filters
  • 深度学习|表示学习|归一化和正则化带给我们的启示|27
  • 前端开发:打造磨砂质感的盒子效果
  • python自动化测试之统一请求封装及通过文件实现接口关联
  • 使用 Flask 构建流式返回服务
  • Logistic Regression 逻辑回归中的sigmoid函数是什么?
  • 【Linux】多线程 -> 从线程概念到线程控制
  • 【CXX】0 Rust与C ++的互操作利器:CXX库介绍与示例