观察者设计模式问题

发布于 2024-12-06 11:26:39 字数 2920 浏览 3 评论 0原文

我正在 php 中创建一个 oop 系统,并希望在其中实现更多观察者模式,因为我希望减少类之间的严重耦合。

我的问题是这样的。 与此模式设计的最佳实践相关的是,一个类可以将观察者添加到该类正在使用的另一个类中。 或者我应该让观察者添加到链的最顶层?

示例:(假设存在其他被调用但未包含在类中的方法,但对于本示例而言并不重要。)

class orderItem extends observable {
     public function pick($qty, $user){
          $this->setUser($user);
          $position = new position($this->getPositionID());
          $position->addObserver(new ProductObserver());  // is this the best option ? ?
          $position->setQty($position->getQty() - $qty);
          $position->save();
          $this->notify(self::EVENT_PICK); // notify observers
     }
}

class orderProductObserver implements observer {
     public function update($orderitem){
           $position = new position($orderitem->getPositionID());
           $product = new product($position->getProductID());
           if($product->getQty() < $product->getMinimum()) {
                $alert = new minProductAlert($product);
           }
     }
}

class ProductObserver implements observer {
     public function update($position){
           $product = new product($position->getProductID());
           if($product->getQty() < $product->getMinimum()) {
                $alert = new minProductAlert($product);
           }
     }
}

$order = new orderItem(123);
$order->addObserver(new orderProductObserver()); // or is this the best option ??
$order->pick(2, 'bill');

或者,如果两种方法都错误,我对您的输入非常感兴趣。

通过消除 orderitem 和position 之间的依赖关系,这个例子是否是最理想的?

 class OrderItem extends Observable {
         public function pick($qty, $user){
              $this->setUser($user);
              $this->setPickedQty($qty);
              $this->save();
              $this->notify(self::EVENT_PICK); // notify observers
         }
    }

    class OrderItemPickObserver implements Observer {
         public function update($orderitem){
               $position = new Position($orderitem->getPositionID());
               $position->addObserver(new ProductPositionObserver());
               $position->setQty($position->getQty() - $orderItem->getPickedQty());
               $position->save();
         }
    }

    class ProductPositionObserver implements Observer {
         public function update($position){
               $product = new product($position->getProductID());
               if($product->getQty() < $product->getMinimum()) {
                    $alert = new minProductAlert($product);
               }
         }
    }
    $pickQty = 2;
    $orderitem = new OrderItem(123);
    $position = new Position($orderitem->getPositionID());
    if($position->getQty() >= $pickQty)
    {
           $orderitem->addObserver(new OrderItemPickObserver()); // or is this the best option ??
           $orderitem->pick($pickQty, 'bill');
    }

i am creating a oop system in php and would like to implement more observer patterns into it as i have heavy coupling between my classes that i wish to reduce.

my question is this.
in relation to best practice in design for this pattern is it ok for one class to add an observer to another class, that class is working with.
or should i keep the observer adding to the top most level of the chain?

example: (assume other methods called, but not included in the class, exist but are not important for this example.)

class orderItem extends observable {
     public function pick($qty, $user){
          $this->setUser($user);
          $position = new position($this->getPositionID());
          $position->addObserver(new ProductObserver());  // is this the best option ? ?
          $position->setQty($position->getQty() - $qty);
          $position->save();
          $this->notify(self::EVENT_PICK); // notify observers
     }
}

class orderProductObserver implements observer {
     public function update($orderitem){
           $position = new position($orderitem->getPositionID());
           $product = new product($position->getProductID());
           if($product->getQty() < $product->getMinimum()) {
                $alert = new minProductAlert($product);
           }
     }
}

class ProductObserver implements observer {
     public function update($position){
           $product = new product($position->getProductID());
           if($product->getQty() < $product->getMinimum()) {
                $alert = new minProductAlert($product);
           }
     }
}

$order = new orderItem(123);
$order->addObserver(new orderProductObserver()); // or is this the best option ??
$order->pick(2, 'bill');

Or alternatively if both methods are wrong i am very interested in your input.

would this example be the most ideal by removing dependency between orderitem and position ?

 class OrderItem extends Observable {
         public function pick($qty, $user){
              $this->setUser($user);
              $this->setPickedQty($qty);
              $this->save();
              $this->notify(self::EVENT_PICK); // notify observers
         }
    }

    class OrderItemPickObserver implements Observer {
         public function update($orderitem){
               $position = new Position($orderitem->getPositionID());
               $position->addObserver(new ProductPositionObserver());
               $position->setQty($position->getQty() - $orderItem->getPickedQty());
               $position->save();
         }
    }

    class ProductPositionObserver implements Observer {
         public function update($position){
               $product = new product($position->getProductID());
               if($product->getQty() < $product->getMinimum()) {
                    $alert = new minProductAlert($product);
               }
         }
    }
    $pickQty = 2;
    $orderitem = new OrderItem(123);
    $position = new Position($orderitem->getPositionID());
    if($position->getQty() >= $pickQty)
    {
           $orderitem->addObserver(new OrderItemPickObserver()); // or is this the best option ??
           $orderitem->pick($pickQty, 'bill');
    }

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

初雪 2024-12-13 11:26:39

第二个示例看起来不错,但我不确定是否在 OrderItemPickObserver 类的更新方法内创建新的 Position 对象。相反,我建议将 Position 对象保留为 OrderItem 类的属性,以便您可以从外部设置它。

class OrderItem extends Observable {
         private $_position;
         public function setPosition($position){
              $this->_position = $position;
         }  
         public function getPosition(){
              return $this->_position;
         }  
    }

然后更新 OrderItemPickObserver 类:

class OrderItemPickObserver implements Observer {
         public function update($orderitem){
               $position = $orderitem->getPosition());
               $position->setQty($position->getQty() - $orderItem->getPickedQty());
               $position->save();
         }
    }

以及您的调用代码:

$orderitem = new OrderItem(123);    
$position = new Position();
$position->addObserver(new ProductPositionObserver());
$orderitem->setPosition($position);

这样您就可以解耦 OrderItemPickObserverPosition 类。

编辑:

如果您的业务逻辑不允许您在 OrderItem 类中拥有 Position 对象,您可以将其移动到 OrderItemPickObserver 因为这是实际使用 Position 对象的类。

class OrderItemPickObserver implements Observer {
             private $_position;
             function __construct($position){
                  $this->_position = $position;
             }  

             public function update($orderitem){
                   $position = $this->_position;
                   $position->setId($orderitem->getPositionID());
                   $position->setQty($position->getQty() - $orderItem->getPickedQty());
                   $position->save();
             }
        }

和你的调用代码:

$orderitem = new OrderItem(123);    
$position = new Position();
$position->addObserver(new ProductPositionObserver());
...
...
$orderitem->addObserver(new OrderItemPickObserver($position)); 

The second example looks good, but I'm not sure if creating new Position object inside update method of OrderItemPickObserver class. Instead, what I would suggest is to keep a Position object as a property of OrderItem class so that you can set it from outside.

class OrderItem extends Observable {
         private $_position;
         public function setPosition($position){
              $this->_position = $position;
         }  
         public function getPosition(){
              return $this->_position;
         }  
    }

Then update OrderItemPickObserver class:

class OrderItemPickObserver implements Observer {
         public function update($orderitem){
               $position = $orderitem->getPosition());
               $position->setQty($position->getQty() - $orderItem->getPickedQty());
               $position->save();
         }
    }

And your calling code:

$orderitem = new OrderItem(123);    
$position = new Position();
$position->addObserver(new ProductPositionObserver());
$orderitem->setPosition($position);

This way you can decouple OrderItemPickObserver and Position classes.

EDITED:

If your business logic doesn't allow you to have a Position object in OrderItem class, you can move the same to OrderItemPickObserver since this is the class which actually uses the Position object.

class OrderItemPickObserver implements Observer {
             private $_position;
             function __construct($position){
                  $this->_position = $position;
             }  

             public function update($orderitem){
                   $position = $this->_position;
                   $position->setId($orderitem->getPositionID());
                   $position->setQty($position->getQty() - $orderItem->getPickedQty());
                   $position->save();
             }
        }

And your calling code:

$orderitem = new OrderItem(123);    
$position = new Position();
$position->addObserver(new ProductPositionObserver());
...
...
$orderitem->addObserver(new OrderItemPickObserver($position)); 
满栀 2024-12-13 11:26:39

我会使用你的第二种方法......它比第一种(依赖注入)更容易阅读和理解 - 这里给出了很好的例子(尽管是旧文档) -> http://www.ibm.com/developerworks/library/os-php-设计模板/

I would use your second method .... its a lot clearer to read and understand than the first (dependency injection)- good examples (although an old document) are given here -> http://www.ibm.com/developerworks/library/os-php-designptrns/

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文