First understand the concept of the Observer pattern: an object makes itself observable by adding a method that allows another object, an observer, to register itself. When an observable object changes, it sends messages to registered observers. These observers use this information to perform operations independent of the observable object. The result is that objects can talk to each other without having to understand why. The observer pattern is an event system, which means that this pattern allows a class to observe the state of another class. When the state of the observed class changes, the observing class can receive notifications and take corresponding actions; observation The operator pattern provides you with the ability to avoid tight coupling between components.
UML structure diagram:
Problems solved by the observer pattern
In our development process, we should have more or less encountered the problem that changing part of the code will cause a series of other changes. Obviously we want to It is unlikely to completely avoid this situation, but we should also try to reduce dependencies on other components as much as possible, and the observer pattern is designed to solve this problem.
For example, we have a post object with the following code:
class Post { protected $_userid = null; protected $_ip = null; protected $_content = null; function __construct() { // ... } // 发帖方法 public function addPost() { // ... 发帖逻辑 } }
The above is an ordinary post object. As the number of posts and visits increases, the operators start to quit. The company also often receives complaint calls saying that our website contains a lot of sensitive content and spam advertisements, so we need to conduct content review: first, review of users, some blacklisted users should be prohibited from posting; second, review of IP ; The third is the review of content-sensitive words. So our code looks like the following:
class Post { protected $_userid = null; protected $_ip = null; protected $_content = null; function __construct() { } public function addPost() { if (!Postscan::checkUserid($tihs->_userid)) { return false; } if (!Postscan::ipUserid($tihs->_ip)) { return false; } if (!Postscan::checkContent($tihs->_content)) { return false; } // ... } }
As more and more fields need to be reviewed, the addPost method becomes longer and longer, and the publishing object can only be tightly embedded in the system. middle.
Implementation of Observer Pattern
The core of the observer pattern is to separate the observer from the subject. When the subject knows that an event occurs, the observer needs to be notified. At the same time, we do not want to create a conflict between the subject and the observer. The relationship is hard-coded, so let’s modify our code above:
//主体必须实现的接口 interface Observable { public function attach(Observer $observer); public function detach(Observer $observer); public function notify(); } //观察者必须实现的接口 interface Observer { public function do(Observable $subject); } class Post implements Observable { protected $_userid = null; protected $_ip = null; protected $_content = null; protected $_observerlist = array(); function __construct() { } public function attach(Observer $observer) { $this->_observerlist[] = $observer; } public function detach(Observer $observer) { foreach ($this->_observerlist as $key => $value) { if ($observer === $value) { unset($this->_observerlist[$key]) } } } public function notify() { foreach ($this->_observerlist as $value) { if (!$value->do($this)) { return false; } } return true; } public function addPost() { if (!$this->notify()) { return false; } // ... } }
With the above code, we can easily add audit rules.
SPL code
The observer pattern is a very common and commonly used design pattern, so much so that the SPL extension has encapsulated the corresponding classes and methods for us. The following code is based on the three elements provided by SPL: SplObserver, SplSubject , the code implemented by SplObjectStorage
class Post implements SplSubject { protected $_userid = null; protected $_ip = null; protected $_content = null; protected $_storage = new SplObjectStorage(); function __construct() { } public function attach(SplObject $observer) { $this->_storage->attach($observer); } public function detach(SplObject $observer) { $this->_storage->detach($observer); } public function notify() { foreach ($this->_storage as $value) { if (!$value->update($this)) { return false; } } return true; } public function addPost() { if (!$this->notify()) { return false; } // ... } }
is very simple. The most important thing is to understand that in this example, we have separated some auditing methods from the post class, and the post object can also be used as Other publishing types.
The implementation of the above content is the observer mode of PHP design pattern introduced by the editor to you. I hope it will be helpful to everyone!
The above introduces the observer pattern example of PHP design pattern, including the relevant content. I hope it will be helpful to friends who are interested in PHP tutorials.