深入解析责任链模式及其在软件设计中的应用与优势

责任链模型:将能够处理某种类型请求的对象串成一条链,请求沿着链传递,链上的对象逐一判断自己是否有能力处理该请求。这使得多个对象有机会处理请求,从而避免请求被发送。发送者和接收者之间的耦合关系。

深入解析责任链模式及其在软件设计中的应用与优势

(图片来源:设计模式:可重用面向对象软件的基础)

优点:发出请求的客户端并不知道链中的哪个对象最终处理该请求,这使得系统可以动态地重新组织和分配职责,而不会影响客户端。

模式实现

案例:员工请求(休假和加薪)必须得到总监->经理->总经理的批准。

处理程序:

定义一个用于处理请求的接口,具有内置的后继者(可选):

代码语言:javascript

复制

public abstract class Leader {
    protected Leader superior;
    protected String name;
    protected Leader(Leader superior, String name) {
        this.superior = superior;
        this.name = name;
    }
    public abstract void handle(Request request);
}

具体处理器

处理它负责的请求,并为其后继者提供访问权限;

如果请求可以被处理,则处理它,否则转发请求:

代码语言:javascript

复制

// 总监
class Director extends Leader {
    public Director(Leader superior, String name) {
        super(superior, name);
    }
    @Override
    public void handle(Request request) {
        if (request.getType().equals("请假") && request.getCount() <= 10) {
            System.out.println("[ " + request.getContent() + "] 请假 [" + request.getCount() + "]天, 总监 [" + name + "] 审批通过");
        } else {
            if (superior != null) {
                superior.handle(request);
            }
        }
    }
}
// 经理
class Manager extends Leader {
    public Manager(Leader superior, String name) {
        super(superior, name);
    }
    @Override
    public void handle(Request request) {
        if (request.getType().equals("请假") && request.getCount() <= 20) {
            System.out.println("[ " + request.getContent() + "] 请假 [" + request.getCount() + "]天, 经理 [" + name + "] 审批通过");
        } else if (request.getType().equals("涨薪") && request.getCount() <= 1000) {
            System.out.println("[ " + request.getContent() + "]  涨薪 [" + request.getCount() + "]RMB, 经理 [" + name + "] 审批通过");
        } else {
            if (superior != null) {
                superior.handle(request);
            }
        }
    }
}
// 总经理
class GeneralManager extends Leader {
    public GeneralManager(Leader superior, String name) {
        super(superior, name);
    }
    @Override
    public void handle(Request request) {
        if (request.getType().equals("请假")) {
            if (request.getCount() <= 30) {
                System.out.println("[ " + request.getContent() + "] 请假 [" + request.getCount() + "]天, 总经理 [" + name + "] 审批通过");
            } else {
                System.out.println("[ " + request.getContent() + "] 你干脆辞职算了");
            }
        } else if (request.getType().equals("涨薪")) {
            if (request.getCount() <= 10_000) {
                System.out.println("[ " + request.getContent() + "]  涨薪 [" + request.getCount() + "]RMB, 总经理 [" + name + "] 审批通过");
            } else {
                System.out.println("你咋不上天呢");
            }
        }
    }
}

客户

向链上特定的handler对象提交请求:

代码语言:javascript

复制

public class Client {
    @Test
    public void client() {
        Leader generalManger = new GeneralManager(null, "刘备");
        Leader manager = new Manager(generalManger, "诸葛亮");
        Leader director = new Director(manager, "赵云");
        director.handle(new Request("请假", "翡青", 32));
        director.handle(new Request("涨薪", "zjf", 1500));
    }
}
public class Request {
    private String type;
    private String content;
    private int count;
    public Request() {
    }
    public Request(String type, String content, int count) {
        this.type = type;
        this.content = content;
        this.count = count;
    }
    public String getType() {
        return type;
    }
    public void setType(String type) {
        this.type = type;
    }
    public String getContent() {
        return content;
    }
    public void setContent(String content) {
        this.content = content;
    }
    public int getCount() {
        return count;
    }
    public void setCount(int count) {
        this.count = count;
    }
}

注:非链表实现了责任链——责任链也可以以集合、数组等形式存储。在很多项目中,每个具体的Handler并不是由开发团队定义的,而是由外部添加的项目上线后的单位。在这种情况下,使用链表方法很难定义责任链。在这种情况下,您可以选择使用集合存储。

概括

优点和缺点

减少耦合:客户端提交请求,请求沿着链传递,直到最终被ConcreteHandler处理。接收方和发送方都没有明确的彼此信息,有利于接收方和发送方的解耦。

增强了为对象分配职责的灵活性:链中的对象本身不知道链结构。他们只维护一个后继指针。因此,责任链可以简化对象的互连,并且可以随时添加或修改处理请求的对象。增强了向对象分配职责的灵活性。

缺陷:无法保证接受:由于请求没有明确的接收者,因此无法保证它会被正确处理,即请求可能直到到达链尾或链序时才会被处理未正确配置。没有“正确”处理。

场景

有多个对象可以处理一种类型的请求,由哪个对象处理是在运行时自动确定的;

向多个对象提交相同的请求,而没有明确指定接收者;

处理请求的对象集合是动态指定的;

Java异常机制:一次try对应多次catch;

Servlet:过滤器链处理;

Spring MVC:拦截器链(具体参见:Spring MVC实践);

相关图案

复合模式:在这种情况下,组件的父组件充当其后继组件。

你可能想看:
« 上一篇
下一篇 »

相关推荐

java中什么是冒泡,冒泡算法

2026年09月06日

27阅读

java中冒号,java双冒号

2026年09月06日

26阅读

java中的->,java中的是什么意思

2026年09月06日

24阅读

java中的super用法,Java中super的说明

2026年09月06日

28阅读

java中反射的应用,java中反射的应用场景

2026年09月06日

25阅读

java中开关的定义,Java关键字有哪些

2026年09月06日

25阅读