1. 最难理解最绕的<br />表示一个作用于某对象结构中的个元素的操作,它是你可以在不改变个元素的类的前提下定义作用于这些元素的新操作<br />适用于对象结构很少改变的类,比如,男 ,收入 支出,<br />乱乱乱,访问类跟对象结构类,互相调用,互相传入,<br />例如,你在朋友家做客,你是访问者,朋友接收你的访问,你通过朋友的描述,然后对朋友的描述做出一个判断,这就是访问者模式。![image.png](https://cdn.nlark.com/yuque/0/2021/png/22438777/1635501305458-b9d2ef82-3bd2-46cd-b916-8a1fdbf86586.png#clientId=u1f6fad2c-ecdc-4&from=paste&height=529&id=u3ac5c27a&margin=%5Bobject%20Object%5D&name=image.png&originHeight=529&originWidth=787&originalType=binary&ratio=1&size=80205&status=done&style=none&taskId=u16d34a80-0510-48ee-a437-849e3c86b50&width=787)
    <?php
    
    //访问抽象类
    interface Visitor
    {
        public function VisitConcreteElementA($a);
    
        function VisitConcreteElementB($b);
    }
    
    //访问实例化类
    class ConcreteVisitor1 implements Visitor
    {
        //传入结构类,
        public function VisitConcreteElementA($a)
        {
            echo get_class($a) . "被" . get_class($this) . "访问", PHP_EOL;
        }
    
        public function VisitConcreteElementB($b)
        {
            echo get_class($b) . "被" . get_class($this) . "访问", PHP_EOL;
        }
    }
    
    class ConcreteVisitor2 implements Visitor
    {
        public function VisitConcreteElementA($a)
        {
            echo get_class($a) . "被" . get_class($this) . "访问", PHP_EOL;
        }
    
        public function VisitConcreteElementB($b)
        {
            echo get_class($b) . "被" . get_class($this) . "访问", PHP_EOL;
        }
    }
    
    //结构抽象类
    interface Element
    {
        public function Accept(Visitor $v);
    }
    
    //结构类
    class ConcreteElementA implements Element
    {
        //传入访问类
        public function Accept(Visitor $v)
        {
            //执行访问类方法,传入自身
            $v->VisitConcreteElementA($this);
        }
    
        public function OperationA()
        {
    
        }
    }
    
    class ConcreteElementB implements Element
    {
        public function Accept(Visitor $v)
        {
            $v->VisitConcreteElementB($this);
        }
    
        public function OperationB()
        {
    
        }
    }
    
    //控制器,存储结构类
    class ObjectStructure
    {
        private $elements = [];
    
        //添加
        public function Attach($element)
        {
            $this->elements[] = $element;
        }
        //删除
        public function Detach($element)
        {
            $position = 0;
            foreach ($this->elements as $e) {
                if ($e == $element) {
                    unset($this->elements[$position]);
                    break;
                }
                $position++;
            }
        }
        //执行结构类中的方法Accept
        public function Accept($visitor)
        {
            foreach ($this->elements as $e) {
                $e->Accept($visitor);
            }
        }
    }
    //控制器
    $o = new ObjectStructure();
    //添加结构
    $o->Attach(new ConcreteElementA());
    $o->Attach(new ConcreteElementB());
    //实例化访问
    $v1 = new ConcreteVisitor1();
    $v2 = new ConcreteVisitor2();
    
    //执行
    $o->Accept($v1);
    $o->Accept($v2);