美文网首页
责任链模式

责任链模式

作者: joychic | 来源:发表于2018-04-02 23:51 被阅读0次

    定义

    使多个对象都有机会处理请求,从而避免了请求的发送者和接收者致敬的耦合关系。将这些对象连成一条链,并沿着这条链传递该请求,直到有对象处理它为止。

    使用场景

    • 多个对象可以处理同一请求,但是具体有哪个来处理则在运行时动态决定
    • 在请求处理者不明确的情况下向多个对象中的一个提交请求
    • 需要动态指定一组对象处理请求
    • 代码中存在多个if-else语句的情况下,此时可以考虑使用责任链模式来对代码进行重构。

    结构

    • AbstractHandler

      抽象处理角色,声明了处理对象处理请求的方法,并在其中保存一个对下一个处理节点AbstractHandler的引用

    • AbstractRequest

      抽象请求者或者具体请求者,根据不同需求可以选择性采取策略

    简单实现

    模拟请假流程

    public abstract class Leader {
    
      /**
       * 下一节点上的处理者对象
       */
      protected Leader nextHandler;
    
      /**
       * 处理请求
       *
       * @param request 请求对象
       */
      public final void handlerRequest(LeaveRequest request) {
        if (request.getDay() <= limit()) {
          handle(request);
        } else {
          if (null != nextHandler) {
            nextHandler.handlerRequest(request);
          }
        }
      }
    
      /**
       * 请求处理
       *
       * @param request 请求条件
       */
      protected abstract void handle(LeaveRequest request);
    
      /**
       * 有权审批的最大天数
       *
       * @return 最大天数
       */
      public abstract int limit();
    }
    

    Leader类充当AbstractHandler的角色,负责主要的逻辑实现;责任转发的逻辑交由handlerRequest()实现,声明了一个获取限制条件的limit()抽象方法

    public class LeaveRequest {
    
      private String name;
      private int day;
    
      public LeaveRequest(String name, int day) {
        this.name = name;
        this.day = day;
      }
         //get set 省略
         ...
         
      }
    

    LeaveRequest为请求者的信息,这里为了简单,没有使用抽象类

    public class TeamLeader extends Leader {
    
      private String name;
    
      public TeamLeader(String name) {
        this.name = name;
      }
    
      @Override protected void handle(LeaveRequest request) {
        System.out.println(name + "审批员工" + request.getName() + " 的请假条,请假天数为" + request.getDay() + "天");
      }
    
      @Override public int limit() {
        return 3;
      }
    }
    
    public class Manager extends Leader {
    
      private String name;
    
      public Manager(String name) {
        this.name = name;
      }
    
      @Override protected void handle(LeaveRequest request) {
        System.out.println(name + "审批员工" + request.getName() + " 的请假条,请假天数为" + request.getDay() + "天");
      }
    
      @Override public int limit() {
        return 10;
      }
    }
    
    public class Director extends Leader {
    
      private String name;
    
      public Director(String name) {
        this.name = name;
      }
    
      @Override protected void handle(LeaveRequest request) {
        System.out.println(name + "审批员工" + request.getName() + " 的请假条,请假天数为" + request.getDay() + "天");
      }
    
      @Override public int limit() {
        return 15;
      }
    }
    
    public class Boss extends Leader {
    
      private String name;
    
      public Boss(String name) {
        this.name = name;
      }
    
      @Override protected void handle(LeaveRequest request) {
        System.out.println(name + "审批员工 " + request.getName() + " 的请假条,请假天数为" + request.getDay() + "天");
      }
    
      @Override public int limit() {
        return Integer.MAX_VALUE;
      }
    }
    

    具体的几个处理者对象,各自负责各自功能的实现

    public class Test {
    
      public static void main(String[] args) {
    
        // 处理者对象
        Leader handler1 = new TeamLeader("沙僧");
        Leader handler2 = new Manager("八戒");
        Leader handler3 = new Director("悟空");
        Leader handler4 = new Boss(" 唐僧");
    
        //  请求者对象
        LeaveRequest request1 = new LeaveRequest("张三", 2);
        LeaveRequest request2 = new LeaveRequest("李四", 5);
        LeaveRequest request3 = new LeaveRequest("王五", 11);
        LeaveRequest request4 = new LeaveRequest("赵六", 18);
        LeaveRequest request5 = new LeaveRequest("赵六", 30);
    
        //设置责任节点链
        handler1.nextHandler = handler2;
        handler2.nextHandler = handler3;
        handler3.nextHandler = handler4;
    
        System.out.println("---------request1---------------");
        handler1.handlerRequest(request1);
    
        System.out.println("----------request2--------------");
        handler1.handlerRequest(request2);
    
        System.out.println("-----------request3-------------");
        handler1.handlerRequest(request3);
    
        System.out.println("-----------request4-------------");
        handler1.handlerRequest(request4);
    
        System.out.println("-----------request5-------------");
        handler1.handlerRequest(request5);
    
        System.out.println("-----------request1-------------");
        handler3.handlerRequest(request1);
    
        System.out.println("-----------request4-------------");
        handler3.handlerRequest(request4);
      }
    }
    
    

    测试类及结果

    ---------request1---------------
    沙僧审批员工张三 的请假条,请假天数为2天
    ----------request2--------------
    八戒审批员工李四 的请假条,请假天数为5天
    -----------request3-------------
    悟空审批员工王五 的请假条,请假天数为11天
    -----------request4-------------
     唐僧审批员工 赵六 的请假条,请假天数为18天
    -----------request5-------------
     唐僧审批员工 赵六 的请假条,请假天数为30天
    -----------request1-------------
    悟空审批员工张三 的请假条,请假天数为2天
    -----------request4-------------
     唐僧审批员工 赵六 的请假条,请假天数为18天
    

    思考

    责任链模式理解起来比较简单,核心的思想就是在AbstractHandler中保留一个AbstractHandler的引用来进行处理

    责任链模式的主要优点在于可以降低系统耦合度,简化对象的相互连接,同时增强给对象指派职责的灵活性,增加新的处理类也很方便

    对于比较长的责任链,请求的处理可能涉及多个对象,对性能可能会有一定影响

    不能保证请求一定被接收,下游的请求无法传递给上游处理

    相关文章

      网友评论

          本文标题:责任链模式

          本文链接:https://www.haomeiwen.com/subject/hkmfhftx.html