首页 > 其他分享 >设计模式-访问者模式

设计模式-访问者模式

时间:2025-01-16 10:46:38浏览次数:1  
标签:double 模式 Visitor 操作 设计模式 public rectangle 访问者

访问者模式(Visitor Pattern)概述

定义
访问者模式(Visitor Pattern)是一种行为型设计模式,它允许你在不改变一个类的结构的前提下,定义该类的新操作。访问者模式通过将操作封装在访问者对象中,将数据结构和操作分离开来,使得增加新的操作变得更加容易。

访问者模式的核心思想是通过一个访问者对象来对数据结构中的元素进行操作,而无需改变数据结构的类。它将“数据结构”和“操作”分开,从而提高了系统的灵活性和可扩展性。

访问者模式的角色

  1. 抽象访问者(Visitor):定义对每一个元素的访问操作。
  2. 具体访问者(ConcreteVisitor):实现抽象访问者接口,定义对各个元素的具体访问操作。
  3. 元素(Element):定义一个接受访问者的 accept() 方法,这个方法会调用访问者的 visit() 方法。
  4. 具体元素(ConcreteElement):实现 Element 接口并提供 accept() 方法的具体实现。
  5. 对象结构(ObjectStructure):包含一组元素,可以遍历元素并允许访问者访问元素。

示例:对不同类型的图形进行操作

假设我们有不同类型的图形(如圆形和矩形),我们想为这些图形添加不同的操作(如计算面积和周长)。通过访问者模式,我们可以为每种图形定义不同的操作。

Java 实现代码

// 抽象元素类
interface Shape {
    void accept(Visitor visitor); // 接受访问者
}

// 具体元素类 - 圆形
class Circle implements Shape {
    private double radius;

    public Circle(double radius) {
        this.radius = radius;
    }

    public double getRadius() {
        return radius;
    }

    @Override
    public void accept(Visitor visitor) {
        visitor.visit(this);  // 访问圆形
    }
}

// 具体元素类 - 矩形
class Rectangle implements Shape {
    private double width, height;

    public Rectangle(double width, double height) {
        this.width = width;
        this.height = height;
    }

    public double getWidth() {
        return width;
    }

    public double getHeight() {
        return height;
    }

    @Override
    public void accept(Visitor visitor) {
        visitor.visit(this);  // 访问矩形
    }
}

// 抽象访问者
interface Visitor {
    void visit(Circle circle);    // 访问圆形
    void visit(Rectangle rectangle);  // 访问矩形
}

// 具体访问者 - 计算面积
class AreaVisitor implements Visitor {

    @Override
    public void visit(Circle circle) {
        double area = Math.PI * Math.pow(circle.getRadius(), 2);
        System.out.println("圆形的面积: " + area);
    }

    @Override
    public void visit(Rectangle rectangle) {
        double area = rectangle.getWidth() * rectangle.getHeight();
        System.out.println("矩形的面积: " + area);
    }
}

// 具体访问者 - 计算周长
class PerimeterVisitor implements Visitor {

    @Override
    public void visit(Circle circle) {
        double perimeter = 2 * Math.PI * circle.getRadius();
        System.out.println("圆形的周长: " + perimeter);
    }

    @Override
    public void visit(Rectangle rectangle) {
        double perimeter = 2 * (rectangle.getWidth() + rectangle.getHeight());
        System.out.println("矩形的周长: " + perimeter);
    }
}

// 客户端
public class VisitorPatternDemo {
    public static void main(String[] args) {
        // 创建元素
        Shape circle = new Circle(5);
        Shape rectangle = new Rectangle(4, 6);

        // 创建访问者
        Visitor areaVisitor = new AreaVisitor();
        Visitor perimeterVisitor = new PerimeterVisitor();

        // 使用访问者进行操作
        System.out.println("计算面积:");
        circle.accept(areaVisitor);
        rectangle.accept(areaVisitor);

        System.out.println("\n计算周长:");
        circle.accept(perimeterVisitor);
        rectangle.accept(perimeterVisitor);
    }
}

输出结果

计算面积:
圆形的面积: 78.53981633974483
矩形的面积: 24.0

计算周长:
圆形的周长: 31.41592653589793
矩形的周长: 20.0

访问者模式的优点

  1. 易于扩展操作:新增操作只需要增加新的访问者类,而不需要修改元素类。
  2. 对象结构和操作分离:访问者模式将数据结构和操作分离,遵循开闭原则。你可以轻松添加新的操作,而不必改变现有类的代码。
  3. 集中管理操作:所有操作都集中在访问者中,方便进行管理和维护。

访问者模式的缺点

  1. 增加复杂性:引入访问者模式后,系统中会增加额外的类,使得设计变得更加复杂。
  2. 对象结构修改困难:如果对象结构发生变化,可能需要对所有访问者进行修改,这在某些情况下可能导致维护成本增高。

使用场景

  1. 对象结构稳定但操作频繁变化的系统:比如在图形绘制应用中,如果图形种类比较固定,但需要对图形执行不同操作(如绘制、计算面积、计算周长等),就可以使用访问者模式。
  2. 编译器设计:在编译器的语法树中,可以定义不同的访问者来实现不同的操作(如代码优化、代码生成等)。
  3. 复杂数据结构操作:当我们需要对数据结构中的每个元素执行多种不同操作时,使用访问者模式可以避免在数据结构中添加大量的操作代码。

总结

访问者模式通过将操作和数据结构分离,允许你在不改变数据结构的情况下,定义新操作。它非常适合于对象结构相对稳定、操作不断变化的场景。在实现时,访问者模式可以有效降低对象间的耦合度,提高系统的可扩展性。

标签:double,模式,Visitor,操作,设计模式,public,rectangle,访问者
From: https://www.cnblogs.com/pangchunlei/p/18674468

相关文章

  • 数字化办公时代的工时管理新模式
    在当今数字化浪潮的推动下,传统的工时管理方式已经难以满足高效办公的需求。在线文档协作工具作为数字化办公的关键环节,正在深刻改变工时管理的模式与效率。本文将探讨在线协作工具在工时管理中的独特优势及其对现代办公模式的深远影响。一、在线文档协作的数字化优势1.信息同......
  • 【设计模式-结构型】代理模式
    一、什么是代理模式        在港片中,经常能看到一些酷炫的大哥被警察抓了,警察会试图从他们口中套出一些关键信息。但这些大哥们通常会非常冷静地回应:“我有权保持沉默,我要找我的律师。”         这个律师就像是大哥的“法律盾牌”,全权处理所有法律事务。律......
  • 设计模式-解释器模式
    解释器模式(InterpreterPattern)概述定义解释器模式(InterpreterPattern)是一种行为型设计模式,主要用于定义语言的文法,并通过该文法解释语句。它提供了一种评估语言表达式的方法,并且这种方法通常通过一个解释器(Interpreter)来实现。解释器模式的主要思想是构建一个抽象语法树,并定......
  • 设计模式-享元模式
    享元模式(FlyweightPattern)概述定义享元模式(FlyweightPattern)是一种结构型设计模式,它通过共享相同的对象来减少内存的使用,特别适用于对象数量庞大且相似的场景。通过共享相同的对象来减少内存的使用,并确保在需要的时候能够快速地访问和使用对象。享元模式的核心思想是:对于相......
  • 请描述下什么是原型模式?它主要运用在哪些场景?
    原型模式是一种创建型设计模式,它允许通过复制(或克隆)一个已存在的对象来创建新对象,而无需重新实例化。这种模式的核心思想是利用已有的对象作为原型,通过对其进行复制来生成新的对象。在前端开发中,原型模式的应用场景主要包括以下几个方面:对象创建成本较高时:如果创建对象的过程比......
  • 设计模式-中介者模式
    中介者模式(MediatorPattern)概述定义中介者模式(MediatorPattern)是一种行为型设计模式,它通过定义一个中介者对象来封装一系列对象之间的交互,使得这些对象之间不直接交互,从而减少了对象之间的依赖关系,降低了系统的复杂度。在中介者模式中,各个对象通过中介者进行通信,避免了它们之......
  • 一元多项式的求导(附加代码模式)
    题目描述一个一元多项式可以看作由若干个一元单项式按降幂排列成的线性表。请编写程序对输入的一元多项式进行求导,并输出求导的结果。本题是附加代码模式,主函数main会自动附加在同学们提交的代码后面,请同学们在提交的时候注释掉附加代码。附加代码如下:int main(){  ......
  • 服务端开发模式-thinkphp-重新整理workman
    一、登录接口<?php/***登录退出操作*User:龙哥·三年风水*Date:2024/10/29*Time:15:53*/namespaceapp\controller\common;useapp\controller\Emptys;useapp\model\permission\Admin;useapp\model\param\SystemasSystemModel;useEmail\EmailSen......
  • TEMPLATE METHOD(模板方法)—类行为型模式
    1.意图定义一个操作中的算法的骨架,而将一些步骤延迟到子类中。TemplateMethod使得子类可以不改变一个算法的结构即可重定义该算法的某些特定步骤。2.动机考虑一个提供Application和Document类的应用框架。Application类负责打开一......
  • STRATEGY(策略)—对象行为型模式
    1.意图定义一系列的算法,把它们一个个封装起来,并且使它们可相互替换。本模式使得算法可独立于使用它的客户而变化。2.别名政策(Policy)3.动机有许多算法可对一个正文流进行分行。将这些算法硬编进使用它们的类中是不可取的,其原因如下:•需要换行功能的客户程序......