Php设计模式(三):行为型模式
  NKfXyChmpEKq 2023年11月02日 77 0


在上一篇我们讲了结构型模式,结构型模式是讨论类和对象的结构的。总共有7种。而今天我们来介绍一下行为型模式。

     

一、什么是行为型模式?

      行为型模式就是描述类和对象之间的通信和职责的。简而言之,就是类和对象扮演什么角色,还有怎么扮演这个角色的问题。

 

二、行为型模式的种类

     大体上分为三个大类:常见模式、已知模式、深度模式

模版方法模式、命令模式、迭代器模式、观察者模式、中介者模式、状态模式、职责链模式、策略模式

     2、 已知模式包括:备忘录模式

     3、深度模式包括:解释器模式 访问者模式

 

下面来介绍常见模式

 

Ø常见模式

    1、模版方法模式(Template):

实现。        就像一个豆浆机,不管放进去的是红豆还是黑豆,出来的都是豆浆。

          好处:扩展性好,封装不变的代码,扩展可变的代码。

          弊端:灵活性差,不能改变骨架部分。

    应用场景:一类或一组具有共性的事物中。

 

代码实现

 


练练手

/**          


                    * 优才网公开课示例代码          


                    *          


                    * 模板方法模式 Template          


                    *          


                    * @author 优才网全栈工程师教研组          


                    * @see http://www.ucai.cn         


                    */         


                    


          function          output(          $string          ) {          


                    echo             $string          .           "n"          ;          


          }          


                    


          class          Request {          


                    


                    public          $token          =           ''          ;          


                    


                    public          function          __construct() {          


                    $this          ->token    =           '0c6b7289f5334ed2b697dd461eaf9812'          ;          


                    }          


                    


          }          


                    


          class          Response {          


                    


                    public          function          render(          $content          ) {          


                    output(sprintf(          'response-render: %s'          ,           $content          ));          


                    }          


                    


                    public          function          redirect(          $uri          ) {          


                    output(sprintf(          'response-redirect: %s'          ,           $uri          ));          


                    }          


                    


                    public          function          json(          $data          ) {          


                    output(sprintf(          'response-data: %s'          , json_encode(          $data          )));          


                    }          


                    


          }          


                    


                    //父类,抽象类          


          abstract          class          Controller{          


                    //封装了输入输出          


                    protected          $request          ;          


                    protected          $response          ;          


                    


                    //返回数据          


                    protected          $data          =           'data'          ;          


                    


                    public          function          __construct(          $request          ,           $response          ){          


                    $this          ->request =           $request          ;          


                    $this          ->response =           $response          ;          


                    }          


                    


                    //执行请求函数,定义总体算法(template method),final防止被复写(不允许子类改变总体算法)          


                    public          final          function          execute(){          


                    $this          ->before();          


                    if          (          $this          ->valid()){          


                    $this          ->handleRequest();          


                    }          


                    $this          ->after();          


                    }          


                    


                    //定义hook method before,做一些具体请求的前置处理          


                    //非abstract方法,子类可以选择覆盖或不覆盖,默认什么都不做          


                    protected          function          before(){          


                    


                    }          


                    


                    //定义hook method valid,做请求的数据验证          


                    //非abstract方法,子类可以选择覆盖或不覆盖,默认返回验证通过          


                    protected          function          valid(){          


                    return          true;          


                    }          


                    


                    //定义hook method handleRequest,处理请求          


                    //定义为abstract方法,子类必须实现或也声明为抽象方法(由子类的子类负责实现)          


                    abstract          function          handleRequest();          


                    


                    //定义hook method after,做一些请求的后置处理          


                    //非abstract方法,子类可以选择覆盖或不覆盖,默认直接输出数据          


                    protected          function          after(){          


                    $this          ->response->render(          $this          ->data);          


                    }          


          }          


                    


          //子类1,实现父类开放的具体算法          


          class          User           extends          Controller{          


                    //覆盖before方法,实现具体算法,这是一个处理用户数据操作的控制器          


                    //因此,我们选择在before里面判断用户是否已经登录了,这里简单判断下session数据          


                    function          before(){          


                    if          (          empty          (          $_SESSION          [          'auth'          ])){          


                    //没登录就直接跳转了,不再执行后续的操作          


                    $this          ->response->redirect(          "user/login.php"          );          


                    }          


                    }          


                    


                    //覆盖valid方法,这里我们验证用户提交数据中有没有带验证token          


                    function          valid(){          


                    if          (isset(          $this          ->request->token)){          


                    return          true;          


                    }          


                    return          false;          


                    }          


                    


                    //覆盖handleRequest方法,必选,以为父类中声明了abstract了          


                    function          handleRequest(){          


                    //做具体处理,一般根据参数执行不同的业务逻辑          


                    }          


                    


                    //这个类我们选择不覆盖after方法,使用默认处理方式          


          }          


                    


          //子类2,实现父类开放的具体算法          


          class          Post           extends          Controller{          


                    //这个类我们选择不覆盖before方法,使用默认处理方式          


                    


                    //这个类我们选择不覆盖valid方法,使用默认处理方式          


                    


                    //覆盖handleRequest方法,必选,以为父类中声明了abstract了          


                    function          handleRequest(){          


                    //做具体处理,一般根据参数执行不同的业务逻辑          


                    $this          ->data =           array          (          'title'          =>           'ucai'          );          


                    }          


                    


                    //覆盖after方法,使用json格式输出数据          


                    function          after(){          


                    $this          ->response->json(          $this          ->data);          


                    }          


          }          


                    


                    


                    


          class          Client {            


                    


                    public          static          function          test(){            


                    


                    $request                 =           new          Request();          


                    $response                =           new          Response();          


                    


                    //最终调用          


                    $user          =           new          User(          $request          ,           $response          );          


                    $user          ->execute();          


                    


                    


                    //最终调用          


                    $post          =           new          Post(          $request          ,           $response          );          


                    $post          ->execute();          


                    


                    }            


                    


          }            


                    


          Client::test();



 

   2、命令模式(Command) :

都会做出标准的敬礼动作。

         好处:便于添加和修改行为,便于聚合多个命令。

         弊端:造成过多具体的命令类。

         应用场景:对要操作的对象,进行的相同操作。

   

代码实现



练练手

/**          


                    * 优才网公开课示例代码          


                    *          


                    * 命令模式 Command          


                    *          


                    * @author 优才网全栈工程师教研组          


                    * @see http://www.ucai.cn         


                    */         


                    


          function          output(          $string          ) {          


                    echo             $string          .           "n"          ;          


          }          


                    


          class          Document {          


                    


                    private          $name          =           ''          ;          


                    


                    public          function          __construct(          $name          ) {          


                    $this          ->name =           $name          ;          


                    }          


                    


                    public          function          showText() {          


                    output(sprintf(          "showText: %s"          ,           $this          ->name));          


                    }          


                    


                    public          function          undo() {          


                    output(sprintf(          "undo-showText: %s"          ,           $this          ->name));          


                    }          


                    


          }          


                    


          class          Graphics {          


                    


                    private          $name          =           ''          ;          


                    


                    public          function          __construct(          $name          ) {          


                    $this          ->name =           $name          ;          


                    }          


                    


                    public          function          drawCircle() {          


                    output(sprintf(          "drawCircle: %s"          ,           $this          ->name));          


                    }          


                    


                    public          function          undo() {          


                    output(sprintf(          "undo-drawCircle: %s"          ,           $this          ->name));          


                    }          


                    


          }          


                    


          class          Client {          


                    


                    public          static          function          test() {          


                    


                    $document                =           new          Document(          'A'          );          


                    $graphics                =           new          Graphics(          'B'          );          


                    


                    $document          ->showText();          


                    $graphics          ->drawCircle();          


                    


                    $document          ->undo();          


                    


                    }          


                    


          }          


                    


          Client::test();          


                    


                    


          <?php          


                    


          /**          


                    * 优才网公开课示例代码          


                    *          


                    * 命令模式 Command          


                    *          


                    * @author 优才网全栈工程师教研组          


                    * @see http://www.ucai.cn         


                    */         


                    


          function          output(          $string          ) {          


                    echo             $string          .           "n"          ;          


          }          


                    


          interface          Command {          


                    public          function          execute();          


                    public          function          undo();          


          }          


                    


          class          Document           implements          Command {          


                    


                    private          $name          =           ''          ;          


                    


                    public          function          __construct(          $name          ) {          


                    $this          ->name =           $name          ;          


                    }          


                    


                    public          function          execute() {          


                    output(sprintf(          "showText: %s"          ,           $this          ->name));          


                    }          


                    


                    public          function          undo() {          


                    output(sprintf(          "undo-showText: %s"          ,           $this          ->name));          


                    }          


                    


          }          


                    


          class          Graphics           implements          Command {          


                    


                    private          $name          =           ''          ;          


                    


                    public          function          __construct(          $name          ) {          


                    $this          ->name =           $name          ;          


                    }          


                    


                    public          function          execute() {          


                    output(sprintf(          "drawCircle: %s"          ,           $this          ->name));          


                    }          


                    


                    public          function          undo() {          


                    output(sprintf(          "undo-drawCircle: %s"          ,           $this          ->name));          


                    }          


                    


          }          


                    


          class          Client {          


                    


                    public          static          function          test() {          


                    


                    $array                   =           array          ();          


                    


                    array_push          (          $array          ,           new          Document(          'A'          ));          


                    array_push          (          $array          ,           new          Document(          'B'          ));          


                    array_push          (          $array          ,           new          Graphics(          'C'          ));          


                    array_push          (          $array          ,           new          Graphics(          'D'          ));          


                    


                    foreach          (          $array          as          $command          ) {          


                    $command          ->execute();          


                    }          


                    


                    $top                     =           array_pop          (          $array          );          


                    $top          ->undo();          


                    


                    }          


                    


          }          


                    


          Client::test();          


                    


                    


          <?php          


                    


          /**          


                    * 优才网公开课示例代码          


                    *          


                    * 命令模式 Command          


                    *          


                    * @author 优才网全栈工程师教研组          


                    * @see http://www.ucai.cn         


                    */         


                    


          function          output(          $string          ) {          


                    echo             $string          .           "n"          ;          


          }          


                    


          interface          Command {          


                    public          function          execute();          


                    public          function          undo();          


          }          


                    


          class          Document {          


                    


                    private          $name          =           ''          ;          


                    


                    public          function          __construct(          $name          ) {          


                    $this          ->name =           $name          ;          


                    }          


                    


                    public          function          showText() {          


                    output(sprintf(          "showText: %s"          ,           $this          ->name));          


                    }          


                    


                    public          function          undo() {          


                    output(sprintf(          "undo-showText: %s"          ,           $this          ->name));          


                    }          


                    


          }          


                    


          class          Graphics {          


                    


                    private          $name          =           ''          ;          


                    


                    public          function          __construct(          $name          ) {          


                    $this          ->name =           $name          ;          


                    }          


                    


                    public          function          drawCircle() {          


                    output(sprintf(          "drawCircle: %s"          ,           $this          ->name));          


                    }          


                    


                    public          function          undo() {          


                    output(sprintf(          "undo-drawCircle: %s"          ,           $this          ->name));          


                    }          


                    


          }          


                    


          class          DocumentCommand           implements          Command {          


                    


                    private          $obj          =           ''          ;          


                    


                    public          function          __construct(Document           $document          ) {          


                    $this          ->obj =           $document          ;          


                    }          


                    


                    public          function          execute() {          


                    $this          ->obj->showText();          


                    }          


                    


                    public          function          undo() {          


                    $this          ->obj->undo();          


                    }          


                    


          }          


                    


          class          GraphicsCommand           implements          Command {          


                    


                    private          $obj          =           ''          ;          


                    


                    public          function          __construct(Graphics           $graphics          ) {          


                    $this          ->obj =           $graphics          ;          


                    }          


                    


                    public          function          execute() {          


                    $this          ->obj->drawCircle();          


                    }          


                    


                    public          function          undo() {          


                    $this          ->obj->undo();          


                    }          


                    


          }          


                    


                    


          class          Client {          


                    


                    public          static          function          test() {          


                    


                    $array                   =           array          ();          


                    


                    array_push          (          $array          ,           new          DocumentCommand(          new          Document(          'A'          )));          


                    array_push          (          $array          ,           new          DocumentCommand(          new          Document(          'B'          )));          


                    array_push          (          $array          ,           new          GraphicsCommand(          new          Graphics(          'C'          )));          


                    array_push          (          $array          ,           new          GraphicsCommand(          new          Graphics(          'D'          )));          


                    


                    foreach          (          $array          as          $command          ) {          


                    $command          ->execute();          


                    }          


                    


                    $top                     =           array_pop          (          $array          );          


                    $top          ->undo();          


                    


                    }          


                    


          }          


                    


          Client::test();




     3、迭代器模式(Iterator):

都是摇出七个球,不能能摇不是七个球的中奖号码组合。

      好处:以不同方式遍历一个集合。

      弊端:每次遍历都是整个集合,不能单独取出元素。

应用场景:需要操作集合里的全部元素。

 

代码实现



练练手

/**          


                    * 优才网公开课示例代码          


                    *          


                    * 迭代器模式 Iterator          


                    *          


                    * @author 优才网全栈工程师教研组          


                    * @see http://www.ucai.cn         


                    */         


                    


          function          output(          $string          ) {          


                    echo             $string          .           "n"          ;          


          }          


                    


          class          RecordIterator           implements          Iterator{          


                    


                    private          $position          = 0;          


                    


                    //注意:被迭代对象属性是私有的          


                    private          $records          =           array          ();            


                    


                    public          function          __construct(Array           $records          ) {          


                    $this          ->position = 0;          


                    $this          ->records =           $records          ;          


                    }          


                    


                    function          rewind          () {          


                    $this          ->position = 0;          


                    }          


                    


                    function          current() {          


                    return          $this          ->records[          $this          ->position];          


                    }          


                    


                    function          key() {          


                    return          $this          ->position;          


                    }          


                    


                    function          next() {          


                    ++          $this          ->position;          


                    }          


                    


                    function          valid() {          


                    return          isset(          $this          ->records[          $this          ->position]);          


                    }          


          }          


                    


          class          PostListPager {          


                    


                    protected          $record            =           array          ();          


                    protected          $total             = 0;          


                    protected          $page              = 0;          


                    protected          $size              = 0;          


                    


                    public          function          __construct(          $category          ,           $page          ,           $size          ) {          


                    


                    $this          ->page     =           $page          ;          


                    $this          ->size     =           $size          ;          


                    


                    // query db          


                    


                    $total                   = 28;          


                    $this          ->total    =           $total          ;          


                    


                    $record              =           array          (          


                    0 =>           array          (          'id'          =>           '1'          ),          


                    1 =>           array          (          'id'          =>           '2'          ),          


                    2 =>           array          (          'id'          =>           '3'          ),          


                    3 =>           array          (          'id'          =>           '4'          ),          


                    );          


                    


                    //          


                    $this          ->record   =           $record          ;          


                    


                    }          


                    


                    public          function          getIterator() {          


                    return           new          RecordIterator(          $this          ->record);          


                    }          


                    


                    public          function          getMaxPage() {          


                    $max             =           intval          (          $this          ->total /           $this          ->size);          


                    return           $max          ;          


                    }          


                    


                    public          function          getPrevPage() {          


                    return           max(          $this          ->page - 1, 1);          


                    }          


                    


                    public          function          getNextPage() {          


                    return           min(          $this          ->page + 1,           $this          ->getMaxPage());          


                    }          


                    


          }          


                    


          class          Client {            


                    


                    public          static          function          test(){            


                    


                    $pager               =           new          PostListPager(1, 2, 4);          


                    


                    foreach          (          $pager          ->getIterator()           as          $key          =>           $val          ) {          


                    output(sprintf(          'Key[%d],Val[%s]'          ,           $key          , json_encode(          $val          )));          


                    }          


                    


                    output(sprintf(          'MaxPage[%d]'          ,           $pager          ->getMaxPage()));          


                    output(sprintf(          'Prev[%d]'          ,           $pager          ->getPrevPage()));          


                    output(sprintf(          'Next[%d]'          ,           $pager          ->getNextPage()));          


                    


                    $iterator                =           $pager          ->getIterator();          


                    while          (          $iterator          ->valid()){          


                    print_r(          $iterator          ->current());          


                    $iterator          ->next();          


                    }          


                    $iterator          ->          rewind          ();          


                    


                    }            


                    


          }            


                    


          Client::test();



 

 

      4、观察者模式(Observer):

都得到通知并自动更新响应。就像报社一样,今天发布的消息只要         是看这份报纸的人看到的都是同样的内容。如果发布另一份报纸,也是一         样的。

     好处:广播式通信,范围大一呼百应,便于操作一个组团,“公有制”。

     弊端:不能单独操作组团里的个体,不能实行按需分配。

     应用场景:操作多个对象,并操作相同。

           

代码实现

 



练练手

/**          


                    * 优才网公开课示例代码          


                    *          


                    * 观察者模式 Observer          


                    *          


                    * @author 优才网全栈工程师教研组          


                    * @see http://www.ucai.cn         


                    */         


                    


          function          output(          $string          ) {          


                    echo             $string          .           "n"          ;          


          }          


                    


                    


          //订单数据对象简单模拟,这个是实际需要被观察的对象(Subject),但是我们将其独立,然后          


          //通过构造方法传入到我们模式中的Subject中,这样使具体业务更加独立          


          class          Order{          


                    //订单号          


                    private          $id          =           ''          ;          


                    


                    //用户ID          


                    private          $userId          =           ''          ;          


                    


                    //用户名          


                    private          $userName          =           ''          ;          


                    


                    //价格          


                    private          $price          =           ''          ;          


                    


                    //下单时间          


                    private          $orderTime          =           ''          ;          


                    


                    //订单数据填充简单模拟,实际应用中可能会读取用户表单输入并处理          


                    public          function          __set(          $name          ,           $value          ){          


                    if          (isset(          $this          ->          $name          )){          


                    $this          ->          $name          =           $value          ;          


                    }          


                    }          


                    


                    //获取订单属性          


                    public          function          __get(          $name          ){          


                    if          (isset(          $this          ->          $name          )){          


                    return          $this          ->          $name          ;          


                    }          


                    return          ""          ;          


                    }          


          }          


                    


          //假设的DB类,便于测试,实际会存入真实数据库          


          class          FakeDB{          


                    public          function          save(          $data          ){          


                    return          true;          


                    }          


          }          


                    


                    


          class          Client {          


                    


                    public          static          function          test() {          


                    


                    //初始化一个订单数据          


                    $order          =           new          Order();          


                    $order          ->id = 1001;          


                    $order          ->userId = 9527;          


                    $order          ->userName =           "God"          ;          


                    $order          ->price = 20.0;          


                    $order          ->orderTime = time();          


                    


                    //向数据库保存订单          


                    $db          =           new          FakeDB();          


                    $result          =           $db          ->save(          $order          );          


                    if          (          $result          ){          


                    


                    //实际应用可能会写到日志文件中,这里直接输出          


                    output(           "[OrderId:{$order->id}] [UseId:{$order->userId}] [Price:{$order->price}]"          );          


                    


                    //实际应用会调用邮件发送服务如sendmail,这里直接输出          


                    output(           "Dear {$order->userName}: Your order {$order->id} was confirmed!"          );          


                    


                    //实际应用会调用邮件发送服务如sendmail,这里直接输出          


                    output(           "Dear Manager: User {$order->userName}(ID:{$order->userId}) submitted a new order {$order->id}, please handle it ASAP!"          );          


                    


                    }          


                    


                    }          


                    


          }          


                    


          Client::test();          


                    


                    


          <?php          


                    


          /**          


                    * 优才网公开课示例代码          


                    *          


                    * 观察者模式 Observer          


                    *          


                    * @author 优才网全栈工程师教研组          


                    * @see http://www.ucai.cn         


                    */         


                    


          function          output(          $string          ) {          


                    echo             $string          .           "n"          ;          


          }          


                    


                    


          //订单数据对象简单模拟,这个是实际需要被观察的对象(Subject),但是我们将其独立,然后          


          //通过构造方法传入到我们模式中的Subject中,这样使具体业务更加独立          


          class          Order{          


                    //订单号          


                    private          $id          =           ''          ;          


                    


                    //用户ID          


                    private          $userId          =           ''          ;          


                    


                    //用户名          


                    private          $userName          =           ''          ;          


                    


                    //价格          


                    private          $price          =           ''          ;          


                    


                    //下单时间          


                    private          $orderTime          =           ''          ;          


                    


                    //订单数据填充简单模拟,实际应用中可能会读取用户表单输入并处理          


                    public          function          __set(          $name          ,           $value          ){          


                    if          (isset(          $this          ->          $name          )){          


                    $this          ->          $name          =           $value          ;          


                    }          


                    }          


                    


                    //获取订单属性          


                    public          function          __get(          $name          ){          


                    if          (isset(          $this          ->          $name          )){          


                    return          $this          ->          $name          ;          


                    }          


                    return          ""          ;          


                    }          


          }          


                    


          //被观察者, 负责维护观察者并在变化发生是通知观察者          


          class          OrderSubject           implements          SplSubject {          


                    private          $observers          ;          


                    private          $order          ;          


                    


                    public          function          __construct(Order           $order          ) {          


                    $this          ->observers =           new          SplObjectStorage();          


                    $this          ->order =           $order          ;          


                    }          


                    


                    //增加一个观察者          


                    public          function          attach(SplObserver           $observer          ) {          


                    $this          ->observers->attach(          $observer          );          


                    }          


                    


                    //移除一个观察者          


                    public          function          detach(SplObserver           $observer          ) {          


                    $this          ->observers->detach(          $observer          );          


                    }          


                    


                    //通知所有观察者          


                    public          function          notify() {          


                    foreach          (          $this          ->observers           as          $observer          ) {          


                    $observer          ->update(          $this          );          


                    }          


                    }          


                    


                    //返回主体对象的具体实现,供观察者调用          


                    public          function          getOrder() {          


                    return          $this          ->order;          


                    }          


          }          


                    


          //记录业务数据日志 (ActionLogObserver),实际可能还要抽象一层以处理不同的Action(业务操作),这里省略          


          class          ActionLogObserver           implements          SplObserver{          


                    public          function          update(SplSubject           $subject          ) {          


                    $order          =           $subject          ->getOrder();          


                    //实际应用可能会写到日志文件中,这里直接输出          


                    output(           "[OrderId:{$order->id}] [UseId:{$order->userId}] [Price:{$order->price}]"          );          


                    }          


          }          


                    


          //给用户发送订单确认邮件 (UserMailObserver)          


          class          UserMailObserver           implements          SplObserver{          


                    public          function          update(SplSubject           $subject          ) {          


                    $order          =           $subject          ->getOrder();          


                    //实际应用会调用邮件发送服务如sendmail,这里直接输出          


                    output(           "Dear {$order->userName}: Your order {$order->id} was confirmed!"          );          


                    }          


          }          


                    


          //给管理人员发订单处理通知邮件 (AdminMailObserver)          


          class          AdminMailObserver           implements          SplObserver{          


                    public          function          update(SplSubject           $subject          ) {          


                    $order          =           $subject          ->getOrder();          


                    //实际应用会调用邮件发送服务如sendmail,这里直接输出          


                    output(           "Dear Manager: User {$order->userName}(ID:{$order->userId}) submitted a new order {$order->id}, please handle it ASAP!"          );          


                    }          


          }          


                    


          //假设的DB类,便于测试,实际会存入真实数据库          


          class          FakeDB{          


                    public          function          save(          $data          ){          


                    return          true;          


                    }          


          }          


                    


                    


          class          Client {          


                    


                    public          static          function          test() {          


                    


                    //初始化一个订单数据          


                    $order          =           new          Order();          


                    $order          ->id = 1001;          


                    $order          ->userId = 9527;          


                    $order          ->userName =           "God"          ;          


                    $order          ->price = 20.0;          


                    $order          ->orderTime = time();          


                    


                    //绑定观察者          


                    $subject          =           new          OrderSubject(          $order          );          


                    $actionLogObserver          =           new          ActionLogObserver();          


                    $userMailObserver          =           new          UserMailObserver();          


                    $adminMailObserver          =           new          AdminMailObserver();          


                    $subject          ->attach(          $actionLogObserver          );          


                    $subject          ->attach(          $userMailObserver          );          


                    $subject          ->attach(          $adminMailObserver          );          


                    //向数据库保存订单          


                    $db          =           new          FakeDB();          


                    $result          =           $db          ->save(          $order          );          


                    if          (          $result          ){          


                    //通知观察者          


                    $subject          ->notify();          


                    }          


                    


                    }          


                    


          }          


                    


          Client::test();



 

     

    5、中介者模式(Mediator):

           用中介对象封装一系列的对象交互,中介使各对象不需要显式地相互引       用。

           类似于邮局,邮寄者和收件者不用自己跑很远路,通过邮局就可以。

     好处:简化了对象之间的关系,减少子类的生成。

     弊端:中介对象可能变得非常复杂,系统难以维护。

应用场景:不需要显示地建立交互

 

代码实现



练练手

/**          


                    * 优才网公开课示例代码          


                    *          


                    * 中介者模式 Mediator          


                    *          


                    * @author 优才网全栈工程师教研组          


                    * @see http://www.ucai.cn         


                    */         


                    


                    


          function          output(          $string          ) {          


                    echo             $string          .           "n"          ;          


          }          


                    


                    


                    


                    


          abstract          class          Mediator {           // 中介者角色          


                    abstract          public          function          send(          $message          ,          $colleague          );           


          }           


                    


          abstract          class          Colleague {           // 抽象对象          


                    private          $_mediator          = null;           


                    public          function          __construct(          $mediator          ) {           


                    $this          ->_mediator =           $mediator          ;           


                    }           


                    public          function          send(          $message          ) {           


                    $this          ->_mediator->send(          $message          ,          $this          );           


                    }           


                    abstract          public          function          notify(          $message          );           


          }           


                    


          class          ConcreteMediator           extends          Mediator {           // 具体中介者角色          


                    private          $_colleague1          = null;           


                    private          $_colleague2          = null;           


                    public          function          send(          $message          ,          $colleague          ) {           


                    if          (          $colleague          ==           $this          ->_colleague1) {           


                    $this          ->_colleague1->notify(          $message          );           


                    }           else          {           


                    $this          ->_colleague2->notify(          $message          );           


                    }           


                    }          


                    public          function          set(          $colleague1          ,          $colleague2          ) {           


                    $this          ->_colleague1 =           $colleague1          ;           


                    $this          ->_colleague2 =           $colleague2          ;           


                    }           


          }           


                    


          class          Colleague1           extends          Colleague {           // 具体对象角色          


                    public          function          notify(          $message          ) {          


                    output(sprintf(          'Colleague-1: %s'          ,           $message          ));          


                    }           


          }           


                    


          class          Colleague2           extends          Colleague {           // 具体对象角色          


                    public          function          notify(          $message          ) {           


                    output(sprintf(          'Colleague-2: %s'          ,           $message          ));          


                    }           


          }           


                    


                    


                    


          class          Client {            


                    


                    public          static          function          test(){            


                    


                    // client          


                    $objMediator          =           new          ConcreteMediator();           


                    $objC1          =           new          Colleague1(          $objMediator          );           


                    $objC2          =           new          Colleague2(          $objMediator          );           


                    $objMediator          ->set(          $objC1          ,          $objC2          );           


                    $objC1          ->send(          "to c2 from c1"          );           


                    $objC2          ->send(          "to c1 from c2"          );           


                    


                    }            


                    


          }            


                    


          Client::test();



 

   6、状态模式(State) :

高兴了遛狗。在两种状态下变现出不同的行为。

    好处:避免if语句实用,方便增加新状态,封装了状态转换规则。

    弊端:增加系统类和对象的数量。

    应用场景:用于对象的不同功能的转换。

 

代码实现

 



练练手

/**          


                    * 优才网公开课示例代码          


                    *          


                    * 状态模式 State          


                    *          


                    * @author 优才网全栈工程师教研组          


                    * @see http://www.ucai.cn         


                    */         


                    


          function          output(          $string          ) {          


                    echo             $string          .           "n"          ;          


          }          


                    


          abstract          class          ILift {            


                    


                    //电梯的四个状态            


                    const          OPENING_STATE = 1;            //门敞状态            


                    const          CLOSING_STATE = 2;            //门闭状态            


                    const          RUNNING_STATE = 3;            //运行状态            


                    const          STOPPING_STATE = 4;           //停止状态;            


                    


                    //设置电梯的状态            


                    public          abstract          function          setState(          $state          );            


                    


                    //首先电梯门开启动作            


                    public          abstract          function          open();            


                    


                    //电梯门有开启,那当然也就有关闭了            


                    public          abstract          function          close();            


                    


                    //电梯要能上能下,跑起来            


                    public          abstract          function          run();            


                    


                    //电梯还要能停下来          


                    public          abstract          function          stop();            


                    


          }            


                    


          /**           


                    * 电梯的实现类            


                    */          


          class          Lift           extends          ILift {            


                    


                    private          $state          ;            


                    


                    public          function          setState(          $state          ) {            


                    $this          ->state =           $state          ;            


                    }            


                    


                    //电梯门关闭            


                    public          function          close() {            


                    


                    //电梯在什么状态下才能关闭            


                    switch          (          $this          ->state) {            


                    case          ILift::OPENING_STATE:            //如果是则可以关门,同时修改电梯状态            


                    $this          ->setState(ILift::CLOSING_STATE);            


                    break          ;            


                    case          ILift::CLOSING_STATE:            //如果电梯就是关门状态,则什么都不做            


                    //do nothing;            


                    return          ;            


                    break          ;            


                    case          ILift::RUNNING_STATE:           //如果是正在运行,门本来就是关闭的,也说明都不做            


                    //do nothing;            


                    return          ;            


                    break          ;            


                    case          ILift::STOPPING_STATE:            //如果是停止状态,本也是关闭的,什么也不做            


                    //do nothing;            


                    return          ;            


                    break          ;            


                    }            


                    


                    output(          'Lift colse'          );            


                    


                    }            


                    


                    //电梯门开启            


                    public          function          open() {            


                    //电梯在什么状态才能开启            


                    switch          (          $this          ->state){            


                    case          ILift::OPENING_STATE:           //如果已经在门敞状态,则什么都不做            


                    //do nothing;            


                    return          ;            


                    break          ;            


                    case          ILift::CLOSING_STATE:           //如是电梯时关闭状态,则可以开启            


                    $this          ->setState(ILift::OPENING_STATE);            


                    break          ;            


                    case          ILift::RUNNING_STATE:           //正在运行状态,则不能开门,什么都不做            


                    //do nothing;            


                    return          ;            


                    break          ;            


                    case          ILift::STOPPING_STATE:           //停止状态,淡然要开门了            


                    $this          ->setState(ILift::OPENING_STATE);            


                    break          ;            


                    }            


                    output(          'Lift open'          );            


                    }            


                    ///电梯开始跑起来            


                    public          function          run() {            


                    switch          (          $this          ->state){            


                    case          ILift::OPENING_STATE:           //如果已经在门敞状态,则不你能运行,什么都不做            


                    //do nothing;            


                    return          ;            


                    break          ;            


                    case          ILift::CLOSING_STATE:           //如是电梯时关闭状态,则可以运行            


                    $this          ->setState(ILift::RUNNING_STATE);            


                    break          ;            


                    case          ILift::RUNNING_STATE:           //正在运行状态,则什么都不做            


                    //do nothing;            


                    return          ;            


                    break          ;            


                    case          ILift::STOPPING_STATE:           //停止状态,可以运行            


                    $this          ->setState(ILift::RUNNING_STATE);            


                    }            


                    output(          'Lift run'          );            


                    }            


                    


                    //电梯停止            


                    public          function          stop() {            


                    switch          (          $this          ->state){            


                    case          ILift::OPENING_STATE:           //如果已经在门敞状态,那肯定要先停下来的,什么都不做            


                    //do nothing;            


                    return          ;            


                    break          ;            


                    case          ILift::CLOSING_STATE:           //如是电梯时关闭状态,则当然可以停止了            


                    $this          ->setState(ILift::CLOSING_STATE);            


                    break          ;            


                    case          ILift::RUNNING_STATE:           //正在运行状态,有运行当然那也就有停止了            


                    $this          ->setState(ILift::CLOSING_STATE);            


                    break          ;            


                    case          ILift::STOPPING_STATE:           //停止状态,什么都不做            


                    //do nothing;            


                    return          ;            


                    break          ;            


                    }            


                    output(          'Lift stop'          );            


                    }            


                    


          }            


                    


                    


                    


          class          Client {          


                    


                    public          static          function          test() {          


                    


                    $lift          =           new          Lift();             


                    


                    //电梯的初始条件应该是停止状态             


                    $lift          ->setState(ILift::STOPPING_STATE);             


                    //首先是电梯门开启,人进去             


                    $lift          ->open();             


                    


                    //然后电梯门关闭             


                    $lift          ->close();             


                    


                    //再然后,电梯跑起来,向上或者向下             


                    $lift          ->run();                


                    


                    //最后到达目的地,电梯挺下来             


                    $lift          ->stop();            


                    


                    }          


                    


          }          


                    


          Client::test();          


                    


                    


          <?php          


                    


          /**          


                    * 优才网公开课示例代码          


                    *          


                    * 状态模式 State          


                    *          


                    * @author 优才网全栈工程师教研组          


                    * @see http://www.ucai.cn         


                    */         


                    


          function          output(          $string          ) {          


                    echo             $string          .           "n"          ;          


          }          


                    


          /**           


                    *            


                    * 定义一个电梯的接口            


                    */          


          abstract          class          LiftState{            


                    


                    //定义一个环境角色,也就是封装状态的变换引起的功能变化            


                    protected           $_context          ;            


                    


                    public          function          setContext(Context           $context          ){            


                    $this          ->_context =           $context          ;            


                    }            


                    


                    //首先电梯门开启动作            


                    public          abstract          function          open();            


                    


                    //电梯门有开启,那当然也就有关闭了            


                    public          abstract          function          close();            


                    


                    //电梯要能上能下,跑起来            


                    public          abstract          function          run();            


                    


                    //电梯还要能停下来,停不下来那就扯淡了            


                    public          abstract          function          stop();            


                    


          }            


                    


                    


          /**           


                    * 环境类:定义客户感兴趣的接口。维护一个ConcreteState子类的实例,这个实例定义当前状态。           


                    */          


          class          Context {            


                    //定义出所有的电梯状态            


                    static           $openningState          = null;            


                    static           $closeingState          = null;            


                    static           $runningState           = null;            


                    static           $stoppingState          = null;            


                    


                    public          function          __construct() {            


                    self::          $openningState          =           new          OpenningState();            


                    self::          $closeingState          =           new          ClosingState();            


                    self::          $runningState          =            new          RunningState();            


                    self::          $stoppingState          =           new          StoppingState();            


                    


                    }            


                    


                    //定一个当前电梯状态            


                    private           $_liftState          ;            


                    


                    public          function          getLiftState() {            


                    return          $this          ->_liftState;            


                    }            


                    


                    public          function          setLiftState(          $liftState          ) {            


                    $this          ->_liftState =           $liftState          ;            


                    //把当前的环境通知到各个实现类中            


                    $this          ->_liftState->setContext(          $this          );            


                    }            


                    


                    


                    public          function          open(){            


                    $this          ->_liftState->open();            


                    }            


                    


                    public          function          close(){            


                    $this          ->_liftState->close();            


                    }            


                    


                    public          function          run(){            


                    $this          ->_liftState->run();            


                    }            


                    


                    public          function          stop(){            


                    $this          ->_liftState->stop();            


                    }            


          }            


                    


          /**           


                    * 在电梯门开启的状态下能做什么事情            


                    */          


          class          OpenningState           extends          LiftState {            


                    


                    /**           


                    * 开启当然可以关闭了,我就想测试一下电梯门开关功能           


                    *           


                    */         


                    public          function          close() {            


                    //状态修改            


                    $this          ->_context->setLiftState(Context::          $closeingState          );            


                    //动作委托为CloseState来执行            


                    $this          ->_context->getLiftState()->close();            


                    }            


                    


                    //打开电梯门            


                    public          function          open() {            


                    output(          'lift open...'          );          


                    }            


                    //门开着电梯就想跑,这电梯,吓死你!            


                    public          function          run() {            


                    //do nothing;            


                    }            


                    


                    //开门还不停止?            


                    public          function          stop() {            


                    //do nothing;            


                    }            


                    


          }            


                    


          /**           


                    * 电梯门关闭以后,电梯可以做哪些事情            


                    */          


          class          ClosingState           extends          LiftState {            


                    


                    //电梯门关闭,这是关闭状态要实现的动作            


                    public          function          close() {            


                    output(          'lift close...'          );          


                    


                    }            


                    //电梯门关了再打开,逗你玩呢,那这个允许呀            


                    public          function          open() {            


                    $this          ->_context->setLiftState(Context::          $openningState          );            //置为门敞状态            


                    $this          ->_context->getLiftState()->open();            


                    }            


                    


                    //电梯门关了就跑,这是再正常不过了            


                    public          function          run() {            


                    $this          ->_context->setLiftState(Context::          $runningState          );           //设置为运行状态;            


                    $this          ->_context->getLiftState()->run();            


                    }            


                    


                    //电梯门关着,我就不按楼层            


                    


                    public          function          stop() {            


                    $this          ->_context->setLiftState(Context::          $stoppingState          );            //设置为停止状态;            


                    $this          ->_context->getLiftState()->stop();            


                    }            


                    


          }            


                    


          /**           


                    * 电梯在运行状态下能做哪些动作            


                    */          


          class          RunningState           extends          LiftState {            


                    


                    //电梯门关闭?这是肯定了            


                    public          function          close() {            


                    //do nothing            


                    }            


                    


                    //运行的时候开电梯门?你疯了!电梯不会给你开的            


                    public          function          open() {            


                    //do nothing            


                    }            


                    


                    //这是在运行状态下要实现的方法            


                    public          function          run() {            


                    output(          'lift run...'          );          


                    }            


                    


                    //这个事绝对是合理的,光运行不停止还有谁敢做这个电梯?!估计只有上帝了            


                    public          function          stop() {            


                    $this          ->_context->setLiftState(Context::          $stoppingState          );           //环境设置为停止状态;            


                    $this          ->_context->getLiftState()->stop();            


                    }            


                    


          }            


                    


                    


                    


          /**           


                    * 在停止状态下能做什么事情            


                    */          


          class          StoppingState           extends          LiftState {            


                    


                    //停止状态关门?电梯门本来就是关着的!            


                    public          function          close() {            


                    //do nothing;            


                    }            


                    


                    //停止状态,开门,那是要的!            


                    public          function          open() {            


                    $this          ->_context->setLiftState(Context::          $openningState          );            


                    $this          ->_context->getLiftState()->open();            


                    }            


                    //停止状态再跑起来,正常的很            


                    public          function          run() {            


                    $this          ->_context->setLiftState(Context::          $runningState          );            


                    $this          ->_context->getLiftState()->run();            


                    }            


                    //停止状态是怎么发生的呢?当然是停止方法执行了            


                    public          function          stop() {            


                    output(          'lift stop...'          );          


                    }            


                    


          }            


                    


          /**           


                    * 模拟电梯的动作            


                    */          


          class          Client {            


                    


                    public          static          function          test() {            


                    $context          =           new          Context();            


                    $context          ->setLiftState(          new          ClosingState());            


                    


                    $context          ->open();            


                    $context          ->close();            


                    $context          ->run();            


                    $context          ->stop();            


                    }            


          }            


                    


          Client::test();



 

     

     7、职责链模式 (Chainof Responsibility):

机,不管那一台都可以取到钱。

     好处:简单化对象隐藏链结构,便于添加新职责节点。

     弊端:请求可能没有接受者,或者被多个接收者调用,性能降低。

     应用场景:处理多种请求。

 

代码实现

 



练练手

/**          


                    * 优才网公开课示例代码          


                    *          


                    * 职责链模式 Chain of Responsibility          


                    *          


                    * @author 优才网全栈工程师教研组          


                    * @see http://www.ucai.cn         


                    */         


                    


          function          output(          $string          ) {          


                    echo             $string          .           "n"          ;          


          }          


                    


          /**           


                    * 加入在公司里,如果你的请假时间小于0.5天,那么只需要向leader打声招呼就OK了。           


            如果0.5<=请假天数<=3天,需要先leader打声招呼,然后部门经理签字。           


            如果3<请假天数,需要先leader打声招呼,然后到部门经理签字,最后总经经理确认签字,           


                    如果请假天数超过10天,是任何人都不能批准的。          


                    */         


                    


                    


          /**           


                    * 抽象处理者角色(Handler:Approver):定义一个处理请求的接口,和一个后继连接(可选)           


                    *           


                    */         


          abstract          class          Handler           


          {            


                    


                    protected          $_handler          = null;            


                    protected          $_handlerName          = null;            


                    


                    public          function          setSuccessor(          $handler          )            


                    {            


                    $this          ->_handler =           $handler          ;            


                    }            


                    


                    protected           function          _success(          $request          )            


                    {            


                    output(sprintf(          "%s's request was passed"          ,           $request          ->getName()));           


                    return          true;            


                    }            


                    abstract          function          handleRequest(          $request          );            


          }            


                    


          /**           


                    * 具体处理者角色(ConcreteHandler:President):处理它所负责的请求,可以访问后继者,如果可以处理请求则处理,否则将该请求转给他的后继者。           


                    *           


                    */         


          class          ConcreteHandlerLeader           extends          Handler            


          {            


                    function          __construct(          $handlerName          ){            


                    $this          ->_handlerName =           $handlerName          ;            


                    }            


                    public          function          handleRequest(          $request          )            


                    {            


                    if          (          $request          ->getDay() < 0.5) {            


                    output(sprintf(          '%s was told'          ,           $this          ->_handlerName));                 // 已经跟leader招呼了          


                    return          $this          ->_success(          $request          );            


                    }             


                    if          (          $this          ->_handler           instanceof          Handler) {            


                    return          $this          ->_handler->handleRequest(          $request          );            


                    }            


                    }            


          }            


          /**           


                    * Manager           


                    *           


                    */         


          class          ConcreteHandlerManager           extends          Handler            


          {            


                    function          __construct(          $handlerName          ){            


                    $this          ->_handlerName =           $handlerName          ;            


                    }            


                    


                    public          function          handleRequest(          $request          )            


                    {            


                    if          (0.5 <=           $request          ->getDay() &&           $request          ->getDay()<=3) {            


                    output(sprintf(          '%s signed'          ,           $this          ->_handlerName));                 // 部门经理签字          


                    return          $this          ->_success(          $request          );            


                    }             


                    if          (          $this          ->_handler           instanceof          Handler) {            


                    return          $this          ->_handler->handleRequest(          $request          );            


                    }            


                    }            


                    


          }            


                    


          class          ConcreteHandlerGeneralManager           extends          Handler            


          {            


                    function          __construct(          $handlerName          ){            


                    $this          ->_handlerName =           $handlerName          ;            


                    }            


                    


                    public          function          handleRequest(          $request          )            


                    {            


                    if          (3 <           $request          ->getDay() &&           $request          ->getDay() < 10){            


                    output(sprintf(          '%s signed'          ,           $this          ->_handlerName));                 // 总经理签字          


                    return          $this          ->_success(          $request          );            


                    }            


                    if          (          $this          ->_handler           instanceof          Handler) {            


                    return          $this          ->_handler->handleRequest(          $request          );            


                    }           else          {          


                    output(sprintf(          'no one can approve request more than 10 days'          ));          


                    }          


                    }            


                    


          }            


                    


          /**           


                    * 请假申请           


                    *           


                    */         


          class          Request            


          {            


                    private          $_name          ;            


                    private          $_day          ;            


                    private          $_reason          ;            


                    


                    function          __construct(          $name          =           ''          ,           $day          = 0,           $reason          =           ''          ){            


                    $this          ->_name =           $name          ;            


                    $this          ->_day =           $day          ;            


                    $this          ->_reason =           $reason          ;            


                    }            


                    


                    public          function          setName(          $name          ){            


                    $this          ->_name =           $name          ;            


                    }            


                    


                    public          function          getName(){            


                    return           $this          ->_name;            


                    }            


                    


                    public          function          setDay(          $day          ){            


                    $this          ->_day =           $day          ;            


                    }            


                    


                    public          function          getDay(){            


                    return           $this          ->_day ;            


                    }            


                    


                    public          function          setReason(          $reason          ){            


                    $this          ->_reason =           $reason          ;            


                    }            


                    


                    public          function          getReason( ){            


                    return           $this          ->_reason;            


                    }            


          }            


                    


                    


          class          Client {            


                    


                    public          static          function          test(){            


                    


                    $leader          =           new          ConcreteHandlerLeader(          'leader'          );            


                    $manager          =           new          ConcreteHandlerManager(          'manager'          );            


                    $generalManager          =           new          ConcreteHandlerGeneralManager(          'generalManager'          );            


                    


                    //请求实例            


                    $request          =           new          Request(          'ucai'          ,4,          '休息'          );            


                    


                    $leader          ->setSuccessor(          $manager          );            


                    $manager          ->setSuccessor(          $generalManager          );            


                    $result          =            $leader          ->handleRequest(          $request          );            


                    }            


                    


          }            


                    


          Client::test();



 

 

      8、策略模式(Strategy):

队里的球员,场上的和场下休息的。教练可以让场上的下来,也          可以让场下的上阵。

      好处:定义可重用的一系列算法和行为,并且消除了if else语句。

      弊端:调用端必须知道所有策略类。

      应用场景:用于对象间的替换。

 

代码实现

 



练练手

/**          


                    * 优才网公开课示例代码          


                    *          


                    * 策略模式 Strategy          


                    *          


                    * @author 优才网全栈工程师教研组          


                    * @see http://www.ucai.cn         


                    */         


                    


                    


          function          output(          $string          ) {          


                    echo             $string          .           "n"          ;          


          }          


                    


          //策略基类接口          


                    


          interface          IStrategy {          


                    public          function          OnTheWay();          


          }          


                    


          class          WalkStrategy           implements          IStrategy {          


                    public          function          OnTheWay() {          


                    output(           '在路上步行'          );          


                    }          


          }          


                    


          class          RideBickStrategy           implements          IStrategy {          


                    public          function          OnTheWay() {          


                    output(           '在路上骑自行车'          );          


                    }          


          }          


                    


          class          CarStrategy           implements          IStrategy {          


                    public          function          OnTheWay() {          


                    output(           '在路上开车'          );          


                    }          


          }          


                    


          //选择策略类Context          


          class          Context {          


                    public          function          find(          $strategy          ) {          


                    $strategy          ->OnTheWay();          


                    }          


          }          


                    


          class          Client {            


                    


                    public          static          function          test(){            


                    


                    $travel          =           new          Context();          


                    $travel          ->find(          new          WalkStrategy());          


                    $travel          ->find(          new          RideBickStrategy());          


                    $travel          ->find(          new          CarStrategy());          


                    


                    }            


                    


          }            


                    


          Client::test();



 

Ø已知模式

      1、备忘录模式(Memento):

 

吗?

      好处:给用户提供了一种可以恢复状态的机制。

      弊端:消耗资源。

应用场景:用于需要保存的数据。

 

代码实现



练练手

/**          


                    * 优才网公开课示例代码          


                    *          


                    * 备忘录模式 Memento          


                    *          


                    * @author 优才网全栈工程师教研组          


                    * @see http://www.ucai.cn         


                    */         


                    


          function          output(          $string          ) {          


                    echo             $string          .           "n"          ;          


          }          


                    


                    


          class          Originator {           // 发起人(Originator)角色          


                    private          $_state          ;          


                    public          function          __construct() {          


                    $this          ->_state =           ''          ;          


                    }          


                    public          function          createMemento() {           // 创建备忘录          


                    return          new          Memento(          $this          ->_state);          


                    }          


                    public          function          restoreMemento(Memento           $memento          ) {           // 将发起人恢复到备忘录对象记录的状态上          


                    $this          ->_state =           $memento          ->getState();          


                    }          


                    public          function          setState(          $state          ) {           $this          ->_state =           $state          ; }           


                    public          function          getState() {           return          $this          ->_state; }          


                    public          function          showState() {          


                    output(          $this          ->_state);          


                    }          


                    


          }          


                    


          class          Memento {           // 备忘录(Memento)角色           


                    private          $_state          ;          


                    public          function          __construct(          $state          ) {          


                    $this          ->setState(          $state          );          


                    }          


                    public          function          getState() {           return          $this          ->_state; }           


                    public          function          setState(          $state          ) {           $this          ->_state =           $state          ;}          


          }          


                    


          class          Caretaker {           // 负责人(Caretaker)角色           


                    private          $_memento          ;          


                    public          function          getMemento() {           return          $this          ->_memento; }           


                    public          function          setMemento(Memento           $memento          ) {           $this          ->_memento =           $memento          ; }          


          }          


                    


          class          Client {            


                    


                    public          static          function          test(){            


                    


                    $org          =           new          Originator();          


                    $org          ->setState(          'open'          );          


                    $org          ->showState();          


                    


                    /* 创建备忘 */         


                    $memento          =           $org          ->createMemento();          


                    


                    /* 通过Caretaker保存此备忘 */         


                    $caretaker          =           new          Caretaker();          


                    $caretaker          ->setMemento(          $memento          );          


                    


                    /* 改变目标对象的状态 */         


                    $org          ->setState(          'close'          );          


                    $org          ->showState();          


                    


                    /* 还原操作 */         


                    $org          ->restoreMemento(          $caretaker          ->getMemento());          


                    $org          ->showState();          


                    


                    }            


                    


          }            


                    


          Client::test();           


                    


                    


          return          ;          


                    


                    


          try          {          


                    


                    $db          ->beginTransaction();          


                    


                    $succ            =           $db          ->          exec          (          $sql_1          );          


                    if          (!          $succ          ) {          


                    throw          new          Exception(          'SQL 1 update failed'          );          


                    }          


                    


                    $succ            =           $db          ->          exec          (          $sql_2          );          


                    if          (!          $succ          ) {          


                    throw          new          Exception(          'SQL 2 update failed'          );          


                    }          


                    


                    $succ            =           $db          ->          exec          (          $sql_3          );          


                    if          (!          $succ          ) {          


                    throw          new          Exception(          'SQL 3 update failed'          );          


                    }          


                    


                    $db          ->commit();          


                    


          }           catch          (Exception           $exp          ) {          


                    


                    $db          ->rollBack();          


                    


          }



 

 

Ø深度模式

      1、解释器模式(Interpreter):

鞋都懂滴。

      好处:可扩展性比较好,灵活性大

      弊端:可能难以维护复杂的文法

      应用场景:用于成对或者一对多的需求中

 

     2、访问者模式(Visitor):

前提下定义作用于这些元素的新操作。如银行排号机。

     好处:将相关的事物集中到一个访问者对象中。

     弊端:增加新数据结构很困难。

     应用场景:排队,排号。

 

三、总结

本篇介绍了行为型模式,行为模式涉及到算法和对象职责间的分配,行为类

模式采用继承机制在类间分派行为,TemplateMethod和Interpreter是类行为

模式。行为对象模式使用对象复合而不是继承,一些行为对象模式描述了一组相

互对等的对象如何相互协作以完成其中任何一个对象都单独无法完成的任务,如

Mediator在对象间引入一个mediator对象提供了松耦合所需的间接性;

Chain of Responsibility提供了更松的耦合,它通过一条候选对象链隐式的向一

个对象发松请求,可以运行时刻决定哪些候选者参与到链中;Observer定义并保

持了对象间的依赖关系;其它的行为对象模式常将行为封装封装在一个对象中,

并将请求指派给它,Strategy模式将算法封装在对象中,这样可以方面的改变和

指定一个对象所使用的算法;Command模式将请求封装在对象中,这样它就可

以作为参数来传递,已可以存储在历史列表中或以其它方式使用;State模式封

装一个对象的状态,使得当这个对象的状态对象变化时,该对象可改变它的行

为;Visitor模式封装分布于多个类之间的行为;而Iterator模式则抽象了访问和

遍历一个集合中对象的方式。

 

 

【版权声明】本文内容来自摩杜云社区用户原创、第三方投稿、转载,内容版权归原作者所有。本网站的目的在于传递更多信息,不拥有版权,亦不承担相应法律责任。如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@moduyun.com

  1. 分享:
最后一次编辑于 2023年11月08日 0

暂无评论

推荐阅读
NKfXyChmpEKq