Skip to content

责任链

更新: 6/22/2025 字数: 0 字 时长: 0 分钟

定义

责任链模式 (Chain of Responsibility Pattern) 使多个对象都有机会处理请求,从而避免请求发送者和接收者之间的耦合关系。将这些对象连成一条链,并沿着这条链传递请求,直到有一个对象处理它为止。

角色

  • 抽象处理器 (Handler):定义处理请求的接口
  • 具体处理器 (Concrete Handler):处理请求的具体实现类
  • 客户端 (Client):创建处理链并提交请求

实现

基础责任链

java
// 抽象处理器
public abstract class Handler {
    protected Handler nextHandler;
    
    public void setNext(Handler handler) {
        this.nextHandler = handler;
    }
    
    public abstract void handleRequest(int request);
}

// 具体处理器 A
public class ConcreteHandlerA extends Handler {
    @Override
    public void handleRequest(int request) {
        if (request <= 10) {
            System.out.println("HandlerA 处理请求:" + request);
        } else if (nextHandler != null) {
            nextHandler.handleRequest(request);
        }
    }
}

// 具体处理器 B
public class ConcreteHandlerB extends Handler {
    @Override
    public void handleRequest(int request) {
        if (request > 10 && request <= 20) {
            System.out.println("HandlerB 处理请求:" + request);
        } else if (nextHandler != null) {
            nextHandler.handleRequest(request);
        }
    }
}

// 具体处理器 C
public class ConcreteHandlerC extends Handler {
    @Override
    public void handleRequest(int request) {
        if (request > 20) {
            System.out.println("HandlerC 处理请求:" + request);
        } else if (nextHandler != null) {
            nextHandler.handleRequest(request);
        }
    }
}

// 客户端使用
public class Client {
    public static void main(String[] args) {
        // 创建处理器
        Handler handlerA = new ConcreteHandlerA();
        Handler handlerB = new ConcreteHandlerB();
        Handler handlerC = new ConcreteHandlerC();
        
        // 构建责任链
        handlerA.setNext(handlerB);
        handlerB.setNext(handlerC);
        
        // 提交请求
        int[] requests = {5, 15, 25, 8, 30};
        for (int request : requests) {
            handlerA.handleRequest(request);
        }
    }
}

过滤器链实现

java
// 请求对象
public class Request {
    private String content;
    
    public Request(String content) {
        this.content = content;
    }
    
    public String getContent() {
        return content;
    }
}

// 响应对象
public class Response {
    private String content;
    
    public void setContent(String content) {
        this.content = content;
    }
    
    public String getContent() {
        return content;
    }
}

// 过滤器接口
public interface Filter {
    void doFilter(Request request, Response response, FilterChain chain);
}

// 过滤器链
public class FilterChain {
    private List<Filter> filters = new ArrayList<>();
    private int index = 0;
    
    public FilterChain addFilter(Filter filter) {
        filters.add(filter);
        return this;
    }
    
    public void doFilter(Request request, Response response) {
        if (index < filters.size()) {
            Filter filter = filters.get(index++);
            filter.doFilter(request, response, this);
        }
    }
}

// HTML 转义过滤器
public class HtmlFilter implements Filter {
    @Override
    public void doFilter(Request request, Response response, FilterChain chain) {
        // 处理请求
        String processed = request.getContent()
            .replace("<", "<")
            .replace(">", ">");
        request = new Request(processed);
        
        // 继续链
        chain.doFilter(request, response);
        
        // 处理响应
        response.setContent(response.getContent() + "--HtmlFilter");
    }
}

// 敏感词过滤器
public class SensitiveFilter implements Filter {
    @Override
    public void doFilter(Request request, Response response, FilterChain chain) {
        // 处理请求
        String processed = request.getContent()
            .replace("敏感词", "***");
        request = new Request(processed);
        
        // 继续链
        chain.doFilter(request, response);
        
        // 处理响应
        response.setContent(response.getContent() + "--SensitiveFilter");
    }
}

// 使用示例
public class FilterDemo {
    public static void main(String[] args) {
        // 创建过滤器链
        FilterChain chain = new FilterChain();
        chain.addFilter(new HtmlFilter())
             .addFilter(new SensitiveFilter());
        
        // 创建请求响应对象
        Request request = new Request("<script>敏感词测试</script>");
        Response response = new Response();
        
        // 执行过滤链
        chain.doFilter(request, response);
        
        System.out.println("处理后的请求:" + request.getContent());
        System.out.println("处理后的响应:" + response.getContent());
    }
}

优缺点

优点:

  1. 降低耦合度:请求发送者无需知道具体处理者
  2. 增强系统灵活性:可动态调整责任链
  3. 符合开闭原则:可新增处理者而不修改现有代码
  4. 责任分配明确:每个处理者专注特定职责

缺点:

  1. 请求可能未被处理(链尾未处理)
  2. 调试困难:请求传递路径复杂
  3. 性能影响:长链导致处理延迟
  4. 循环引用风险:处理者相互引用导致死循环

应用场景

  1. 多级审批系统(请假、报销)
  2. 异常处理机制(Java 异常处理)
  3. 过滤器链(Servlet Filter)
  4. 日志处理系统(不同级别日志处理器)
  5. 事件传递机制(GUI 事件处理)
  6. 权限验证系统(多级权限检查)

与其他模式的关系

  • 与命令模式:责任链传递请求,命令封装请求
  • 与组合模式:可组合处理器形成树形结构
  • 与装饰器模式:都使用链式结构,但目的不同
  • 与状态模式:状态转移 vs 请求传递
  • 与中介者模式:中介集中控制,责任链分散处理

JDK 中的责任链模式

  1. Java 异常处理机制(try-catch-finally)
  2. Servlet 过滤器(FilterChain)
  3. AOP 拦截器链(Spring Interceptor)
  4. Java 日志框架(Logger handlers)
  5. Java NIO 事件处理(ChannelPipeline)
  6. Spring Security 过滤器链

注意事项

  1. 明确链的终止条件(避免无限传递)
  2. 控制链的长度(性能考虑)
  3. 考虑请求优先级(前置处理 vs 后置处理)
  4. 处理未处理请求(默认处理器)
  5. 避免循环引用(链成环)
  6. 线程安全问题(共享处理器状态)
  7. 合理设置处理者粒度(避免过大或过小)

贡献者

The avatar of contributor named as LI SIR LI SIR
The avatar of contributor named as wkwbk wkwbk

页面历史