• 《java设计模式》之责任链模式


    在阎宏博士的《JAVA与模式》一书中开头是这样描述责任链(Chain of Responsibility)模式的:

      责任链模式是一种对象的行为模式。在责任链模式里,很多对象由每一个对象对其下家的引用而连接起来形成一条链。请求在这个链上传递,直到链上的某一个对象决定处理此请求。发出这个请求的客户端并不知道链上的哪一个对象最终处理这个请求,这使得系统可以在不影响客户端的情况下动态地重新组织和分配责任。


    在以下条件下可考虑使用Chain of Responsibility:
    1 有多个的对象可以处理一个请求,哪个对象处理该请求运行时刻自动确定。
    2 你想在不明确指定接受者的情况下,想过个对象中的一个提交一个请求。
    3 可处理一个请求的对象集合应该被动态指定。


    一个简单的例子:

     1 abstract class Handler {
     2 
     3     private Handler nextHandler;
     4 
     5     public Handler getNextHandler() {
     6         return nextHandler;
     7     }
     8 
     9     public void setNextHandler(Handler nextHandler) {
    10         this.nextHandler = nextHandler;
    11     }
    12 
    13     public abstract void doHandler();
    14 
    15 }
    16 
    17 class ConcreteHandler extends Handler {
    18 
    19     @Override
    20     public void doHandler() {
    21 
    22         if (getNextHandler() != null) {
    23 
    24             System.out.println("还有责任链");
    25             getNextHandler().doHandler();
    26         } else {
    27 
    28             System.out.println("我自己处理" + toString());
    29         }
    30 
    31     }
    32 }

     既然为设计模式,必然有其鲜明代码的主体框架,我们来分析下

    首先定义一个抽象的处理角色Handler ,其次是具体实现类ConcreteHandler ,在ConcreteHandler 我们通过getNextHandler()来判断是否还有下一个责任链,如果有,则继续

    传递下去,调用getNextHandler().doHandler()来实现。

    分析了简单的责任链模式的代码框架之后,我们接下来给代码加点实际的功能,举个很简单的例子,就是报销流程,项目经理<部门经理<总经理

    其中项目经理报销额度不能大于500,则部门经理的报销额度是不大于1000,超过1000则需要总经理审核

     1 abstract class ConsumeHandler {
     2 
     3     private ConsumeHandler nextHandler;
     4 
     5     public ConsumeHandler getNextHandler() {
     6         return nextHandler;
     7     }
     8 
     9     public void setNextHandler(ConsumeHandler nextHandler) {
    10         this.nextHandler = nextHandler;
    11     }
    12 
    13     /** user申请人 free报销费用 */
    14     public abstract void doHandler(String user, double free);
    15 
    16 }
    17 //项目经理
    18 class ProjectHandler extends ConsumeHandler {
    19 
    20     @Override
    21     public void doHandler(String user, double free) {
    22         if (free < 500) {
    23 
    24             if (user.equals("lwx")) {
    25                 System.out.println("给予报销:" + free);
    26             } else {
    27                 System.out.println("报销不通过");
    28             }
    29 
    30         } else {
    31             if (getNextHandler() != null) {
    32 
    33                 getNextHandler().doHandler(user, free);
    34             }
    35         }
    36 
    37     }
    38 }
    39 //部门经理
    40 class DeptHandler extends ConsumeHandler {
    41     
    42     @Override
    43     public void doHandler(String user, double free) {
    44         if (free < 1000) {
    45             
    46             if (user.equals("zy")) {
    47                 System.out.println("给予报销:" + free);
    48             } else {
    49                 System.out.println("报销不通过");
    50             }
    51             
    52         } else {
    53             if (getNextHandler() != null) {
    54                 
    55                 getNextHandler().doHandler(user, free);
    56             }
    57         }
    58         
    59     }
    60 }
    61 //总经理
    62 class GeneralHandler extends ConsumeHandler {
    63     
    64     @Override
    65     public void doHandler(String user, double free) {
    66         if (free >=1000) {
    67             
    68             if (user.equals("lwxzy")) {
    69                 System.out.println("给予报销:" + free);
    70             } else {
    71                 System.out.println("报销不通过");
    72             }
    73             
    74         } else {
    75             if (getNextHandler() != null) {
    76                 
    77                 getNextHandler().doHandler(user, free);
    78             }
    79         }
    80         
    81     }
    82 }

    测试下

     1 public static void main(String[] args) {
     2 
     3         /*ConcreteHandler handler1 = new ConcreteHandler();
     4         ConcreteHandler handler2 = new ConcreteHandler();
     5         handler1.setNextHandler(handler2);
     6         handler1.doHandler();*/
     7         
     8         ProjectHandler projectHandler =new ProjectHandler();
     9         DeptHandler deptHandler =new DeptHandler();
    10         GeneralHandler generalHandler =new GeneralHandler();
    11         projectHandler.setNextHandler(deptHandler);
    12         deptHandler.setNextHandler(generalHandler);
    13         projectHandler.doHandler("lwx", 450);
    14         projectHandler.doHandler("lwx", 600);
    15         projectHandler.doHandler("zy", 600);
    16         projectHandler.doHandler("zy", 1500);
    17         projectHandler.doHandler("lwxzy", 1500);
    18     }

    执行结果

    给予报销:450.0
    报销不通过
    给予报销:600.0
    报销不通过
    给予报销:1500.0

    拓展联想:模拟实现servlet过滤器中字符和登陆过滤器的实现

    关于tomcat中责任链的使用:http://www.cnblogs.com/java-my-life/archive/2012/05/28/2516865.html

  • 相关阅读:
    jQuery Ajax 方法调用 Asp.Net WebService 的详细例子(原创)
    jQuery 访问WebService 返回复合类型列表
    Vista Media Center 开发之深入浅出 (一) Vista Media Center开发环境的搭建
    安装一个媒体解码器让 Windows Media Player 支持更多媒体格式
    静静期待 Windows 7 的到来
    集成 RealTek 声卡 在 Windows 7 有杂音、爆音的解决方法
    使用jQuery for Asp.Net 我的开发环境配置
    Windows 7 VHD 启动
    建立一个 C#.Net Windows Service 程序
    Windows server 2008 r2 简体中文180天评估版微软官方下载地址
  • 原文地址:https://www.cnblogs.com/draem0507/p/3784130.html
Copyright © 2020-2023  润新知