定义
在对象之间定义一个一对多的依赖,当一个对象状态改变的时候,所有依赖的对象都会自动收到通知。一般情况下,被依赖的对象叫作被观察者(Observable),依赖的对象叫作观察者(Observer)。
实现方式
有同步阻塞的实现方式,也有异步非阻塞的实现方式;有进程内的实现方式,也有跨进程的实现方式。
<?phpabstract class Subject{private $observers = [];public function attach(Observer $observer){array_push($this->observers, $observer);}public function detatch($observer){foreach ($this->observers as $key => $value) {if ($observer === $value) {unset($this->observers[$key]);}}}public function notify(){foreach ($this->observers as $observer) {$observer->update();}}}abstract class Observer{abstract function update();}class ConcreteSubject extends Subject{private $subjectState;public function setState($state){$this->subjectState = $state;}public function getState(){return $this->subjectState;}}class ConcreteObserver extends Observer{private $name;private $subject;function __construct(ConcreteSubject $subject, $name){$this->subject = $subject;$this->name = $name;}public function update(){echo "观察者 ".$this->name."的新状态是:".$this->subject->getState()."\n";}}$s = new ConcreteSubject();$s->attach(new ConcreteObserver($s, "x"));$s->attach(new ConcreteObserver($s, "y"));$z = new ConcreteObserver($s, "z");$s->attach($z);$s->detatch($z);$s->setState('ABC');$s->notify();
应用场景
邮件订阅、RSS Feeds,状态机流转。
总结
将一个系统分割成一系列相互协作的类有一个很不好的副作用,那就是要维护相关对象间的一致性。我们不希望为了维持一致性而使各类紧密耦合,这样会给维护、扩展和重用都带来不便。
观察者模式所做的工作其实就是在接触耦合。让耦合的双方都依赖于抽象,而不是依赖于具体。从而使得各自的变化都不会影响另一边的变化。
