zoukankan      html  css  js  c++  java
  • php 设计模式之责任链模式

     责任链模式
    1. 模式介绍

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

    2.模式组成
      2.1 抽象处理者(Handler)角色:
            定义出一个处理请求的接口。如果需要,接口可以定义 出一个方法以设定和返回对下家的引用。这个角色通常由一个Java抽象类或者Java接口实现。上图中Handler类的聚合关系给出了具体子类对下家的引用,抽象方法handleRequest()规范了子类处理请求的操作。
    2.2 具体处理者(ConcreteHandler)角色:
    具体处理者接到请求后,可以选择将请求处理掉,或者将请求传给下家。由于具体处理者持有对下家的引用,因此,如果需要,具体处理者可以访问下家。
    3 模式结构


    4 项目应用
    4.1 设计一个请假已用,<=2天,经理批准即可; <=5天,总监批准,其它总经理批准。
    4.2 源码分析
    class Request
    {
        public $name;
        public $day;
        public $reason;
    
        public function __construct($name,$day,$reason)
        {
            $this->name = $name;
            $this->day = $day;
            $this->reason = $reason;
        }
    }
    
    abstract class Manager
    {
        //姓名
        protected $name;
    
        //上级
        protected $superior;
    
        public function __construct($name)
        {
            $this->name = $name;
        }
    
        /**
         * 设置上级
         *
         * @param Manager $superior
         * @access public
         * @return void
         */
        public function setSuperior(Manager $superior)
        {
            $this->superior = $superior;
        }
    
        //处理请求
        abstract public function doApplication(Request $request);
    
    
        //打印结果
        public function displayResult(Request $request)
        {
            echo "请假人:{$request->name},请假天数:{$request->day},批准人:{$this->name}
    ";
        }
    }
    
    //经理
    class CommonManager extends Manager
    {
    
        public function doApplication(Request $request)
        {
            if($request->day <= 2)
            {
                $this->displayResult($request);
                return;
            }
    
            //上级处理
            if($this->superior instanceof Majordomo)
            {
                $this->superior->doApplication($request);
            }
            else
            {
                throw new Exception('CommonManager 上级不为 Majordomo');
            }
        }
    
    }
    
    //总监
    class Majordomo extends Manager
    {
    
        public function doApplication(Request $request)
        {
            if($request->day <= 5)
            {
                $this->displayResult($request);
                return;
            }
    
            //上级处理
            if($this->superior instanceof GeneralManager)
            {
                $this->superior->doApplication($request);
            }
            else
            {
                throw new Exception('CommonManager 上级不为 GeneralManager');
            }
        }
    
    }
    
    //总经理
    class GeneralManager extends Manager
    {
    
        public function doApplication(Request $request)
        {
            $this->displayResult($request);
        }
    
    }
    
    function run()
    {/*{{{*/
        $commonManager = new CommonManager('zhangsan');
        $majordomo = new Majordomo('lisi');
        $generalManager = new GeneralManager('wangwu');
    
        //设置责任链
        $commonManager->setSuperior($majordomo);
        $majordomo->setSuperior($generalManager);
    
        for($i = 1; $i < 8;$i++)
        {
            $name = 'test'.$i;
            $day = rand(1,10);
            $reason = '我要请假'.$day;
            $request = new Request($name,$day,$reason);
    
            $commonManager->doApplication($request);
            echo '</br>';
        }
    
    }/*}}}*/
    
    run();
    参考:https://blog.csdn.net/clevercode/article/details/52804839
     
  • 相关阅读:
    c++ stl string char* 向 string 转换的问题
    不要在疲惫中工作
    今天
    悠然自得
    忙与闲
    <转>LuaTinker的bug和缺陷
    匿名管道
    SetWindowHookEx 做消息响应
    最近工作
    实现网页页面跳转的几种方法(meta标签、js实现、php实现)
  • 原文地址:https://www.cnblogs.com/zxqblogrecord/p/9981303.html
Copyright © 2011-2022 走看看