PHP设计模式之观察者模式实例

 更新时间:2016年02月22日 09:15:13   投稿:mrr  
一个对象通过添加一个方法(该方法允许另一个对象,即观察者 注册自己)使本身变得可观察。当可观察的对象更改时,它会将消息发送到已注册的观察者。通过本文给大家介绍PHP设计模式之观察者模式,需要的朋友参考下

首先了解观察者模式的概念:一个对象通过添加一个方法(该方法允许另一个对象,即观察者 注册自己)使本身变得可观察。当可观察的对象更改时,它会将消息发送到已注册的观察者。这些观察者使用该信息执行的操作与可观察的对象无关。结果是对象可以相互对话,而不必了解原因。观察者模式是一种事件系统,意味着这一模式允许某个类观察另一个类的状态,当被观察的类状态发生改变的时候,观察类可以收到通知并且做出相应的动作;观察者模式为您提供了避免组件之间紧密耦。

UML结构图:

观察者模式解决的问题

在我们的开发过程中,应该都或多或少的碰到过改动其中一部分代码会引起其他一连串改变的问题,显然想要完全避免这种情况不太可能,但我们也应答尽量减少对其他组件的依赖,而观察者模式就是为了解决这个问题。

举个例子来说,我们有一个帖子对象,代码如下:

class Post
{
protected $_userid = null;
protected $_ip = null;
protected $_content = null;
function __construct()
{
// ...
}
// 发帖方法
public function addPost()
{
// ... 发帖逻辑
}
}

在上面是一个普通的帖子对象,随着发帖量和访问量越来越大,运营们开始不干了,公司也经常会接到投诉电话,说我们的网站有许多敏感内容和垃圾广告,因此我们需要做内容审核:首先是对用户的审核,一些黑名单用户应该被禁止发帖;二是对IP的审核;三是对内容敏感词的审核。因此我们的代码就成了如下的样子:

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;
}
// ... 
}
}

随着需要审核的字段越来越多,addPost方法变得越来越长,发布对象被也只能紧紧的被嵌入到该系统中。

观察者模式的实现

观察者模式的核心是把观察者从主体中分离开来,当主体知道事件发生时,观察需要被通知到,同时我们也不想把主体和观察者之间的关系写死,于是我们来修改下我们上面的代码:

//主体必须实现的接口
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;
}
// ... 
}
}

通过上面的代码,我们可以再很容易的加入审核规则。

SPL代码

观察者模式是一个很常见和常用的设计模式,以至于SPL扩展已经为我们封装好了对应的类和方法,下面的代码是根据SPL提供的3个元素:SplObserver,SplSubject,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;
}
// ... 
}
}

很简单吧,最重要的是理解,在这个例子中,我们把一些审核的方法从帖子类中剥离了开来,而且该帖子对象也可以用来作为其他的发布类型。

以上内容实现是小编给大家介绍的PHP设计模式之观察者模式,希望对大家有所帮助!

相关文章

  • PHP 超高性能可扩展HTTP服务框架Webman

    PHP 超高性能可扩展HTTP服务框架Webman

    本文主要介绍了超高性能可扩展HTTP服务框架Webman,webman用于替代传统的php-fpm架构,提供超高性能可扩展的HTTP服务,感兴趣的可以了解一下
    2024-02-02
  • PHP中使用extract函数

    PHP中使用extract函数

    这篇文章主要介绍了PHP中使用extract函数,本篇文章通过简要的案例,讲解了该项技术的了解与使用,以下就是详细内容,需要的朋友可以参考下
    2021-07-07
  • CentOS 上搭建 PHP7 开发测试环境

    CentOS 上搭建 PHP7 开发测试环境

    本文给大家分享的是作者在centos上搭建部署php7的开发测试环境的全部过程,非常的细致,有需要的小伙伴可以参考下
    2017-02-02
  • Windows PHP5和Apache的安装与配置

    Windows PHP5和Apache的安装与配置

    在这里以PHP5为例介绍一下Windows下Apache和PHP5的安装与配置方法。
    2009-06-06
  • php中ob函数缓冲机制深入理解

    php中ob函数缓冲机制深入理解

    这篇文章主要介绍了php中ob函数缓冲机制,有需要的小伙伴们可以来学习下
    2015-08-08
  • 部署和发布PHP网站到IIS服务器的全过程

    部署和发布PHP网站到IIS服务器的全过程

    这篇文章主要介绍了如何在IIS服务器上部署PHP网站,PHP的优势在于易学易用、开源免费、跨平台性、强大社区支持、与MySQL的良好集成、丰富的框架和库、安全性以及高效的服务器端处理能力,文中通过图文介绍的非常详细,需要的朋友可以参考下
    2025-02-02
  • WordPress主题中添加文章列表页页码导航的PHP代码实例

    WordPress主题中添加文章列表页页码导航的PHP代码实例

    这篇文章主要介绍了WordPress主题中添加文章列表页码导航的PHP代码实例,这也是制作各种WordPress主题必备的基础功能,需要的朋友可以参考下
    2015-12-12
  • thinkphp实现附件上传功能

    thinkphp实现附件上传功能

    这篇文章主要为大家详细介绍了thinkphp实现附件上传功能,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2017-05-05
  • PHP中使用CURL发送get/post请求上传图片批处理功能

    PHP中使用CURL发送get/post请求上传图片批处理功能

    这篇文章主要介绍了PHP中使用CURL发送get/post请求上传图片批处理 功能,本文通过实例代码给大家介绍的非常详细,非常不错,具有一定的参考借鉴价值,需要的朋友可以参考下
    2018-10-10
  • php设计模式之职责链模式定义与用法经典示例

    php设计模式之职责链模式定义与用法经典示例

    这篇文章主要介绍了php设计模式之职责链模式定义与用法,结合完整实例形式详细分析了php职责链模式的概念、原理、定义与使用方法,注释中包含详细的说明,需要的朋友可以参考下
    2019-09-09

最新评论