• B6:命令模式 Command


    将一个请求封装成一个对象,从而可以用不同的请求对象对客户进行参数化,对请求排队或记录请求日志,以及支持可撤销的操作.

    与状态模式和责任链模式的区别是,命令模式设定一次,统一执行

    使用场景:
    1.可设计一个队列
    2.较容易将命令计入日志
    3.允许接收的一方是决定是否否决请求
    4.可以实现对请求的撤销和重做
    5.加入新的命令类不影响其他的类.
    6.把请求一个操作的对象与执行操作的对象分离开.

    UML

    示例代码:

    // 命令接口
    abstract class  Command
    {
        protected $receiver;
    
        public function __construct(Receiver $receiver)
        {
            $this->receiver = $receiver;
        }
        // 执行命令
        abstract public  function execute($params);
        // 撤销命令
        abstract public function undo();
    }
    
    // 具体命令执行者
    class UserCommand extends Command
    {
        public function execute($params)
        {
            return $this->receiver->command($params);
        }
    
        public function undo()
        {
            return $this->receiver->undo();
        }
    }
    
    // 具体命令执行者2
    class EmailCommand extends Command
    {
        public function execute($params)
        {
            return $this->receiver->command($params);
        }
    
        public function undo()
        {
            return $this->receiver->undo();
        }
    
    }
    
    // 命令接受者接口
    interface Receiver
    {
        public function command($params);
        public function undo();
    }
    
    // 命令接受者1
    class User implements Receiver
    {
        public function command($parms)
        {
            echo '写入:用户增加成功' . $parms;
        }
    
        public function undo()
        {
            echo '撤销了日志写入';
        }
    }
    
    
    // 命令接受者2
    class Email implements Receiver
    {
        public function command($parms)
        {
            echo '发送邮件' . $parms;
        }
    
        public function undo()
        {
            echo '撤销了发送邮件';
        }
    }
    
    
    
    // 命令请求者
    class Invoker
    {
        protected $command;
    
        public function setCommand(Command $command)
        {
            $this->command = $command;
        }
    
        public function execute($params)
        {
            return $this->command->execute($params);
        }
    
        public function undo()
        {
            return $this->command->undo();
        }
    }
    
    $receiver1 = new User();
    $receiver2 = new Email();
    
    $invoker = new Invoker();
    $invoker->setCommand(new UserCommand($receiver1));
    $invoker->execute('jack');
    $invoker->undo();
    
    $invoker->setCommand(new EmailCommand($receiver2));
    $invoker->execute('jack');
    $invoker->undo();
    

     

    另一个例子:

    客户点菜,服务员向厨师发送炒菜命令

    /**
     * 厨师,命令接受者与执行者
     * Class Cook
     */
    class Cook
    {
        public function chaocai()
        {
            echo '开始炒菜了';
        }
    
        public function zuotang()
        {
            echo '开始做汤';
        }
    }
    
    // 命令接口
    abstract class Command
    {
        protected $cook;
    
        public function __construct(Cook $cook)
        {
            $this->cook = $cook;
        }
    }
    
    // 命令1
    class Chaocai extends Command
    {
        public function chaocaiCommand()
        {
            $this->cook->chaocai();
        }
    }
    
    // 命令2
    class Zuotang extends Command
    {
        public function zuotangCommand()
        {
            $this->cook->zuotang();
        }
    }
    
    
    // 命令请求者,服务员
    class Fuyuwuan
    {
        private $chaocai;
        private $zuotang;
    
        public function __construct(Chaocai $chaocai, Zuotang $zuotang)
        {
            $this->chaocai = $chaocai;
            $this->zuotang = $zuotang;
        }
    
        public function callChaocai()
        {
            $this->chaocai->chaocaiCommand();
        }
    
        public function callZuotang()
        {
            $this->zuotang->zuotangCommand();
        }
    }
    
    // 客户
    $cook = new Cook(); // 新建厨师
    // 命令
    $chaocai = new Chaocai($cook);
    $zuotang = new Zuotang($cook);
    
    $fuwuyuan = new Fuyuwuan($chaocai, $zuotang); // 新建服务员
    $fuwuyuan->callChaocai();  // 向服务员点单
    

      

     

  • 相关阅读:
    Cocos2d Box2D之动态刚体
    Cocos2d Box2D之简介
    Cocos2d-x之物理引擎
    Cocos2d-x之UI控件简介
    Cocos2d-x之数据的处理
    My First Django Project (3)
    My First Django Project (2)
    My First Django Project
    Python 学习笔记
    利用python scrapy 框架抓取豆瓣小组数据
  • 原文地址:https://www.cnblogs.com/itfenqing/p/7791492.html
Copyright © 2020-2023  润新知