浅谈PHP设计模式的访问者模式

yizhihongxing

简介:

访问者模式,属于行为型的设计模式。表示一个作用于某对象结构中的各元素的操作。它是你可以在不改变各元素的类的前提下定义作用于这些元素的新操作。

适用场景:

  1. 类中有易于变化的算法。
  2. 希望数据结构与数据分离。

优点:

  1. 便于增加新的操作,相当于增加一个访问者。访问者模式将有关行为集中到一个访问者对象中。

缺点:

元素变更比较困难,如为被访问的对象增加、减少一些属性,相应的访问者也需要进行修改 ;

代码:

/**
 *Component接口声明了一个“accept”方法,该方法应将base访问者接口作为参数。
 */
interface Component
{
    public function accept(Visitor $visitor): void;
}

/**
 *每个具体组件必须以这样的方式实现“accept”方法:它调用与组件类对应的访问者方法。
 */
class ConcreteComponentA implements Component
{
    /*
     * 注意,我们调用的是与当前类名匹配的“visitContainerComponentA”。通过这种方式,我们让访问者知道它所使用的组件的类
     */
    public function accept(Visitor $visitor): void
    {
        $visitor->visitConcreteComponentA($this);
    }

    /*
     * 具体组件可能具有其基类或接口中不存在的特殊方法。Visitor仍然能够使用这些方法,因为它知道组件的具体类
     */
    public function exclusiveMethodOfConcreteComponentA(): string
    {
        return "A";
    }
}

class ConcreteComponentB implements Component
{
    /**
     * 此处相同:visitContainerComponentB=>ConcreteComponentB
     */
    public function accept(Visitor $visitor): void
    {
        $visitor->visitConcreteComponentB($this);
    }

    public function specialMethodOfConcreteComponentB(): string
    {
        return "B";
    }
}

/**
 *Visitor接口声明了一组与组件类相对应的访问方法。访问方法的签名允许访问者标识它正在处理的组件的确切类。
 */
interface Visitor
{
    public function visitConcreteComponentA(ConcreteComponentA $element): void;

    public function visitConcreteComponentB(ConcreteComponentB $element): void;
}

/**
 *Concrete Visitors实现了同一算法的多个版本,它可以与所有具体组件类一起工作。当将Visitor模式与复杂的对象结构(如Composite树)一起使用时,您可以体验到它的最大好处。在这种情况下,在对结构的各个对象执行访问者的方法时,存储算法的一些中间状态可能会有所帮助。
 */
class ConcreteVisitor1 implements Visitor
{
    public function visitConcreteComponentA(ConcreteComponentA $element): void
    {
        echo $element->exclusiveMethodOfConcreteComponentA() . " + ConcreteVisitor1\n";
    }

    public function visitConcreteComponentB(ConcreteComponentB $element): void
    {
        echo $element->specialMethodOfConcreteComponentB() . " + ConcreteVisitor1\n";
    }
}

class ConcreteVisitor2 implements Visitor
{
    public function visitConcreteComponentA(ConcreteComponentA $element): void
    {
        echo $element->exclusiveMethodOfConcreteComponentA() . " + ConcreteVisitor2\n";
    }

    public function visitConcreteComponentB(ConcreteComponentB $element): void
    {
        echo $element->specialMethodOfConcreteComponentB() . " + ConcreteVisitor2\n";
    }
}

/**
 *客户端代码可以在任何一组元素上运行访问者操作,而无需弄清楚它们的具体类。accept操作将调用指向访问者对象中的适当操作。
 */
function clientCode(array $components, Visitor $visitor)
{
    // ...
    foreach ($components as $component) {
        $component->accept($visitor);
    }
    // ...
}


//调用端
$components = [
    new ConcreteComponentA(),
    new ConcreteComponentB(),
];

echo "客户端代码通过基本访问者界面与所有访问者一起工作:\n";
$visitor1 = new ConcreteVisitor1();
clientCode($components, $visitor1);
echo "\n";

echo "它允许相同的客户端代码与不同类型的访问者一起工作:\n";
$visitor2 = new ConcreteVisitor2();
clientCode($components, $visitor2);

原文链接:https://www.cnblogs.com/phpphp/p/17069476.html

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:浅谈PHP设计模式的访问者模式 - Python技术站

(0)
上一篇 2023年4月18日
下一篇 2023年4月18日

相关文章

  • PHP的cURL库功能简介 抓取网页、POST数据及其他

    PHP的cURL库功能简介 什么是cURL cURL是一种用来传输数据的工具和库。它支持各种各样的协议,包括HTTP、HTTPS、FTP、SMTP、POP3、LDAP、以及各种基于字节流的协议。 cURL在Linux和Unix系统中常常用来实现命令行下的文件传输。而PHP中提供了对cURL库的完整封装,简化了cURL库的使用,可以让我们方便地在PHP中使用c…

    PHP 2023年5月23日
    00
  • 详解微信小程序支付流程与梳理

    详解微信小程序支付流程与梳理 什么是微信小程序支付? 微信小程序支付是一种在线支付方式,由微信支付提供,让用户在小程序内完成支付操作。微信小程序支付为用户提供了一种方便、安全、快捷的支付方式,无需离开小程序,即可完成支付操作。 微信小程序支付流程 微信小程序支付的整个流程可以分为以下几个步骤: 1. 用户在小程序内提交订单 用户在小程序内选择付款商品,并填写…

    PHP 2023年5月30日
    00
  • PHP响应post请求上传文件的方法

    下面是详细讲解“PHP响应post请求上传文件的方法”的完整攻略。 前置知识 在讲解上传文件的过程之前,我们需要先了解以下几点相关知识: HTML的表单提交方式 表单提交方式有两种,分别是GET和POST。 enctype属性 enctype属性规定在提交表单时要使用哪种内容类型。当表单包含 enctype=”multipart/form-data” 属性时…

    PHP 2023年5月26日
    00
  • PHP实现的文件操作类及文件下载功能示例

    PHP 实现的文件操作类可以帮助我们更加方便地管理和操作文件,包括创建、读取、写入、修改和删除文件等操作。同时,文件下载功能是一个非常常见的功能,我们可以通过 PHP 来实现文件下载。 以下是实现文件操作类及文件下载的完整攻略: 一、创建文件操作类 1.1 创建文件操作类的基本结构 创建文件操作类的基本结构如下所示: class FileHandler { …

    PHP 2023年5月26日
    00
  • 如何使用GDB调试PHP程序

    下面是关于如何使用GDB调试PHP程序的完整攻略: 1. 安装GDB 首先,我们需要在系统上安装GDB。在Ubuntu和Debian等Linux发行版中可以通过命令行安装: sudo apt-get install gdb 在MacOS上,可以通过Homebrew命令行包管理工具进行安装: brew install gdb 2. 开启PHP的调试模式 要使用…

    PHP 2023年5月23日
    00
  • 解析php获取字符串的编码格式的方法(函数)

    在PHP中,要获取一个字符串的编码格式,可以使用以下3种方法: mb_detect_encoding函数 mb_detect_encoding函数是PHP内置的多字节字符集检测函数,可以用于检测字符串的编码格式。使用该函数前,需要确保PHP的mbstring扩展已经安装并启用。 该函数的语法如下: string mb_detect_encoding ( st…

    PHP 2023年5月26日
    00
  • MATLAB生成复数的方法

    生成复数在MATLAB中非常简单,可以使用以下几种方法: 1. 使用角度和模数 使用 abs 和 angle 函数来定义一个复数的模数和角度,并存储在 r 和 theta 变量中。然后使用 complex 函数将它们组合为一个复数。 r = 3; % 定义模数为3 theta = pi/4; % 定义角度为 pi/4 z = complex(r*cos(th…

    PHP 2023年5月27日
    00
  • PHP构造二叉树算法示例

    PHP构造二叉树算法示例 二叉树(Binary Tree),是由节点组成,每个节点最多有两个子树的树结构。在二叉树中,如果把所有非叶子节点的度看做2,则每个节点的度为0、1或2,因此可以看做是一种特殊的树。 如何在PHP中构造二叉树呢?下面将详细讲解PHP构造二叉树算法示例的完整攻略。 步骤1. 定义节点类 二叉树由节点组成,因此第一步是定义节点类。 cla…

    PHP 2023年5月27日
    00
合作推广
合作推广
分享本页
返回顶部