定义:责任链模式(Chain of Responsibility),使多个对象都有机会处理请求,从而避免请求的发送者和接受者之间的耦合关系。将这些关系对象连成一条链,并沿着这条链传递该请求,直到有一个对象处理它为止。
结构图:
所涉及的角色:
抽象处理者(Handler)角色:定义出一个处理请求的接口。如果需要,接口可以定义 出一个方法以设定和返回对下家的引用。这个角色通常由一个Java抽象类或者Java接口实现。上图中Handler类的聚合关系给出了具体子类对下家的引用,抽象方法handleRequest()规范了子类处理请求的操作。
具体处理者(ConcreteHandler)角色:具体处理者接到请求后,可以选择将请求处理掉,或者将请求传给下家。由于具体处理者持有对下家的引用,因此,如果需要,具体处理者可以访问下家。
代码示例:
全局变量,接口类型 Levels
package com.jin.model.chain; // 全局变量,接口类型 /** * 使用Java中的interface定义全局变量,可根据具体需要在 具体的包中使用静态导入相关的全局变量,语法如下: import static * package01.package02.*; */ public interface Levels { public static final int LEVEL_01 = 1; public static final int LEVEL_02 = 2; public static final int LEVEL_03 = 3; }
抽象请求类:AbstractRequest
package com.jin.model.chain; // 抽象请求类 public abstract class AbstractRequest { private String content; public AbstractRequest(String content) { this.content = content; } public String getContent() { return this.content; } // 获得请求的级别 public abstract int getRequestLevel(); }
具体请求类01:Request01
package com.jin.model.chain; // 具体请求类01 public class Request01 extends AbstractRequest { public Request01(String content) { super(content); } @Override public int getRequestLevel() { return Levels.LEVEL_01; } }
具体请求类02:Request02
package com.jin.model.chain; // 具体请求类02 public class Request02 extends AbstractRequest { public Request02(String content) { super(content); } @Override public int getRequestLevel() { return Levels.LEVEL_02; } }
具体请求类03:Request03
package com.jin.model.chain; // 具体请求类03 public class Request03 extends AbstractRequest { public Request03(String content) { super(content); } @Override public int getRequestLevel() { return Levels.LEVEL_03; } }
抽象处理者类:AbstractHandler
package com.jin.model.chain; // 抽象处理者类, public abstract class AbstractHandler { // 责任链的下一个节点,即处理者 private AbstractHandler nextHandler = null; // 捕获具体请求并进行处理,或是将请求传递到责任链的下一级别 public final void handleRequest(AbstractRequest request) { // 若该请求与当前处理者的级别层次相对应,则由自己进行处理 if (this.getHandlerLevel() == request.getRequestLevel()) { this.handle(request); } else { // 当前处理者不能胜任,则传递至职责链的下一节点 if (this.nextHandler != null) { System.out.println("当前 处理者-0" + this.getHandlerLevel() + " 不足以处理 请求-0" + request.getRequestLevel()); // 这里使用了递归调用 this.nextHandler.handleRequest(request); } else { System.out.println("职责链上的所有处理者都不能胜任该请求..."); } } } // 设置责任链中的下一个处理者 public void setNextHandler(AbstractHandler nextHandler) { this.nextHandler = nextHandler; } // 获取当前处理者的级别 protected abstract int getHandlerLevel(); // 定义链中每个处理者具体的处理方式 protected abstract void handle(AbstractRequest request); }
具体处理者-01:Handler01
package com.jin.model.chain; // 具体处理者-01 public class Handler01 extends AbstractHandler { @Override protected int getHandlerLevel() { return Levels.LEVEL_01; } @Override protected void handle(AbstractRequest request) { System.out.println("处理者-01 处理 " + request.getContent() + "\n"); } }
具体处理者-02:Handler02
package com.jin.model.chain; // 具体处理者-02 public class Handler02 extends AbstractHandler { @Override protected int getHandlerLevel() { return Levels.LEVEL_02; } @Override protected void handle(AbstractRequest request) { System.out.println("处理者-02 处理 " + request.getContent() + "\n"); } }
具体处理者-03:Handler03
package com.jin.model.chain; // 具体处理者-03 public class Handler03 extends AbstractHandler { @Override protected int getHandlerLevel() { return Levels.LEVEL_03; } @Override protected void handle(AbstractRequest request) { System.out.println("处理者-03 处理 " + request.getContent() + "\n"); } }
客户端:Client
package com.jin.model.chain; // 测试类 public class Client { public static void main(String[] args) { // 创建指责链的所有节点 AbstractHandler handler01 = new Handler01(); AbstractHandler handler02 = new Handler02(); AbstractHandler handler03 = new Handler03(); // 进行链的组装,即头尾相连,一层套一层 handler01.setNextHandler(handler02); handler02.setNextHandler(handler03); // 创建请求并提交到指责链中进行处理 AbstractRequest request01 = new Request01("请求-01"); AbstractRequest request02 = new Request02("请求-02"); AbstractRequest request03 = new Request03("请求-03"); // 每次提交都是从链头开始遍历 handler01.handleRequest(request01); handler01.handleRequest(request02); handler01.handleRequest(request03); } }
运行结果:
好处:
- 接受者和发送者都没有对方的明确信息,且链中的对象自己也不知道链的结构,结果是责任链可简化对象的相互连接,它们仅需保持一个指向其后继者的引用,而不需保持它所有的候选者的引用,大大降低了耦合度。
- 由客户端来定义链的结构,可以随时随地增加或修改处理一个请求的结构,增加了给对象指派职责的灵活性。
- 发出请求的客户端并不知道哪一个对象最终处理这个请求,这样系统的更改可以在不影响客户端的情况下动态地重新组织和分配责任。
不足之处:
- 对于每一个请求都需要遍历职责链,性能是个问题;
- 抽象处理者 AbstractHandler 类中的 handleRequest() 方法中使用了递归,栈空间的大小也是个问题。