观察者模式(又称为发布-订阅(Publish/Subscribe)模式,是一种行为模式,将行为独立模块化,降低行为与主体之间的耦合性。它定义了一个一对多的依赖关系,允许多个观察者对象同时监视一个主题对象,当主题对象改变状态时,会通知所有观察者对象,让它们自动更新自己。),抽象主题角色将所有的观察者对象保存在一个集合中,每个主题可以有任意数量的观察者,抽象主题提供了一个接口,可以添加和删除观察者对象。ConcreteSubject:具体主题(具体观察),这个角色存储了特定观察者对象中的相关状态,当特定对象内部状态发生变化时,向所有注册的观察者发送通知。Observer:Abstractobserver,是观察者的一个抽象类,它定义了一个更新接口,当通知对象发生变化时更新自己。ConcrereObserver:具体的观察者实现了抽象观察者定义的更新接口,在被通知主体改变状态时更新自己。PHP有一个内置的SplSubjectabstractsubjectInterfaceSplObserverabstractobserverInterface接口约束//SubjectobserverinterfaceSplSubject{publicfunctionattach(SplObserver$observer);//注册观察者到当前主题publicfunctiondetach(SplObserver$observer);//从当前主题中删除观察者publicfunctionnotify();//主题状态更新时通知所有观察者做相应的处理}//观察者接口SplObserver{publicfunctionupdate(SplSubject$subject);//RegisterobserverstoCurrenttopic}通过项目中的实际应用,更容易理解观察者模式。下面我们以用户为主题,邮件模块和短信模块为观察者。当用户注册成功后,邮件观察者或短信观察者会收到相应的Notifications,向用户发送邮件和短信UserTopicname=$name;$this->email=$email;$this->mobile=$mobile;//业务处理并注册成功$reg_result=true;如果($reg_result){$this->notify();//所有注册成功的观察者都会收到这个主题的通知returntrue;}返回假;}/***当前主题注册一个新的观察者*@paramSplObserver$observer[description]*@return[type][description]*/publicfunctionattach(SplObserver$observer){returnarray_push($this->observers,$观察者);}/***当前主题删除已注册的观察者*@paramSplObserver$observer[description]*@return[type][description]*/publicfunctiondetach(SplObserver$observer){$key=array_search($observer,$this->观察者,真);if(false!==$key){unset($this->observers[$key]);返回真;}返回假;}/***状态更新通知所有观察者*@return[type][description]*/publicfunctionnotify(){if(!empty($this->observers)){foreach($this->observersas$key=>$observer){$observer->update($this);}}返回真;}}Email/SmsObserver/***观察者通过update接收主题更新通知*/classEmailObserverimplementsSplObserver{/***观察者接收主题通知的接口*@paramSplSubject$user[description]*@return[type][说明]*/publicfunctionupdate(SplSubject$user){echo"sendemailto".$用户->电子邮件。PHP_EOL;}}classSmsObserverimplementsSplObserver{publicfunctionupdate(SplSubject$user){echo"sendsmsto".$用户->手机。PHP_EOL;}}业务//用户主题$user=newUser();//为用户观察注册邮箱$emailObserver=newEmailObserver();$user->attach($emailObserver);//为用户注册短信观察者(短信观察者订阅用户主题)$smsObserver=newSmsObserver();$user->attach($smsObserver);//从中删除短信观察者用户(Sms观察者取消订阅User主题)//$user->detach($smsObserver);//注册器会根据注册结果通知观察者Observers做相应处理$user->register("bigcat","32448732@qq.com","1888888888");result发邮件到32448732@qq.com发短信到1888888888【0.1s完成】其实观察者模式类似于事件注册和hook回调。在日常开发中,我们可能会对外重构和分离一些类的行为,封装成独立的功能模块。在班级注册时,我们可以使用事件注册或者观察者模式345374113@qq.com贡献FUNC版/*********观察者模式FUNC版********/$user=['name'=>'','email'=>'','mobile'=>'','updates'=>[],'OnUpdate'=>function($update)use(&$user){array_push($user['更新'],$update);},'Update'=>function()use(&$user){foreach($user['updates']as$update)$update($user);},'Register'=>function($name,$email,$mobile)使用(&$user){$user['name']=$name;$user['email']=$email;$用户['手机']=$手机;$用户['更新']();},];$user["OnUpdate"](function($subject){echo"sendemailto".$subject['email'].PHP_EOL;});$user["OnUpdate"](function($subject)){echo"发送短信到".$subject['mobile'].PHP_EOL;});$user['Register']("紫羽·大薯","345374113@qq.com","1888888888");
