访问器模式

访问器(visitor)模式

意图:主要将数据结构与数据操作分离。
主要解决:稳定的数据结构和易变的操作耦合问题。

代码:

#include <iostream>
#include <list>
using namespace std;

class ComputerPartVisitor;

class ComputerPart
{
public:
    virtual ~ComputerPart() {}
public:
    virtual void accept(ComputerPartVisitor *v) = 0;
};

class KeyBoard;
class Mouse;
class Monitor;

class ComputerPartVisitor
{
public:
    virtual ~ComputerPartVisitor() {}
public:
    virtual void visit(KeyBoard *keyboard) = 0;
    virtual void visit(Mouse *mouse) = 0;
    virtual void visit(Monitor *monitor) = 0;
};

class KeyBoard : public ComputerPart
{
public:
    virtual void accept(ComputerPartVisitor *v)
    {
        v->visit(this);
    }
};

class Mouse : public ComputerPart
{
public:
    virtual void accept(ComputerPartVisitor *v)
    {
        v->visit(this);
    }
};

class Monitor : public ComputerPart
{
public:
    virtual void accept(ComputerPartVisitor *v)
    {
        v->visit(this);
    }
};

class ComputerPartDisplayVisitor : public ComputerPartVisitor
{
public:
    virtual void visit(KeyBoard *keyboard)
    {
        cout << "Displaying KeyBoard." << endl;
    }

    virtual void visit(Mouse *mouse)
    {
        cout << "Displaying Mouse." << endl;
    }

    virtual void visit(Monitor *monitor)
    {
        cout << "Displaying Monitor." << endl;
    }
};

class Computer
{
public:
    Computer()
    {
        _computerPartList.clear();
        addComponent(new KeyBoard);
        addComponent(new Mouse);
        addComponent(new Monitor);
    }

    ~Computer()
    {
        for (auto it = _computerPartList.begin(); it != _computerPartList.end(); ++it)
        {
            delete *it;
        }
        _computerPartList.clear();
    }

public:
    void addComponent(ComputerPart *cp)
    {
        _computerPartList.push_back(cp);
    }

    void accept(ComputerPartVisitor *v)
    {
        for (auto it = _computerPartList.begin(); it != _computerPartList.end(); ++it)
        {
            (*it)->accept(v);
        }
    }
private:
    list<ComputerPart*> _computerPartList;
};

void test()
{
    Computer *c = new Computer();
    ComputerPartVisitor *visitor = new ComputerPartDisplayVisitor();
    c->accept(visitor);
    delete c;
    delete visitor;
}

int main()
{
    test();
    cin.get();
    return 0;
}

效果:

时间: 2024-10-14 07:44:57

访问器模式的相关文章

GOF23设计模式之解释器模式和访问器模式的理解

设计模式之解释器模式Interpreter      是一种不常用的设计模式      用于描述如何构成一个简单的语言解释器,主要用于使用面向对象语言开发的编译器和解释器设计.      当我们需要开发一种新的语言时,可以考虑使用解释器模式.      尽量不要使用解释器模式,后期维护会有很大麻烦.在项目中可以使用jruby,Groovy,java的js引擎来代替解释器的作用,弥补java语言的不足. 开发中常见的场景:      EL表达式的处理      正则表达式解释器      SQL语

设计模式---行为变化模式之访问器模式(Visitor)

一:概念 访问者模式,是行为模式之一,它分离对象的数据和行为,使用Visitor模式,可以不修改已有类的情况下,增加新的操作角色和职责. 二:动机 在软件构建的过程中,由于需求的改变,某些类层次结构中常常需要增加新的行为(方法).如果直接在类中做这样的更改,将会给子类带来很繁重的变更负担,甚至破坏原有设计. 如何在不更改类层次结构的前提下,在运行时根据需要透明地为类层次结构上的各个类动态添加新的操作,从而避免上述问题? 三:代码讲解 (一)原代码 #include <iostream> usi

装饰器模式与代理模式比较

当有这样的业务需求的时候——要为写好的代码在目标代码之前或者之后添加部分操作时,此时最笨的方法就是直接在目标代码的前后加上我们需要的功能代码,但是这样违背了java封装的特性.更好一点的方法就是使用设计模式——代理模式,然而,装饰器模式也有同类的功能,那么着两种设计模式到底有什么区别呢?下面就分别来学习一下这两种设计模式. 装饰器模式类图如下: 该类图包括几个部分:一个接口(装饰器与需要被装饰的实体类都需要实现该接口,公用方法在该接口中定义),一个实现类,一个装饰器的接口,具体实现的装饰器. 在

IOS设计模式之二(门面模式,装饰器模式)

本文原文请见:http://www.raywenderlich.com/46988/ios-design-patterns. 由 @krq_tiger(http://weibo.com/xmuzyq)翻译,如果你发现有什么错误,请与我联系谢谢. 门面(Facade)模式(译者注:facade有些书籍译为门面,有些书籍译为外观,此处译为门面) 门面模式针对复杂的子系统提供了单一的接口,不需要暴漏一些列的类和API给用户,你仅仅暴漏一个简单统一的API. 下面的图解释了这个概念: 这个API的使用者

optimizer_mode优化器模式

查询优化器最主要的工作就是接受输入的SQL以及各种环境参数.配置参数,生成合适的SQL执行计划(Execution Plan). Query Optimizer一共经历了两个历史阶段: RBO: Rule-Based Optimization 基于规则的优化器 CBO: Cost-Based Optimization 基于代价的优化器 关于RBO与CBO,一个形象的比喻:大数据时代到来以前,做生意或许凭借多年累计 下来的经验规则(RBO)就能够很好的做出决策,跟随市场变化.但是大数据时代,如果做

属性类型:数据类型,访问器类型的坑

ECMA5弄了一个新东西, 就是用户可以通过Object.defineProperty配置属性的可写,可配置,可枚举, 让我们开发者可以定义一些属性,这些属性有点像native的赶脚 比如,我们平常定义一个对象这样子就可以了: var obj0 = { name : "nono" }; 我们也可以用新的方式,Object的属性设置方法defineProperty设置属性, 如果用户没有传enumberable, configurable, writable的值, 默认是false, 也

vs2010 .net4.0 错误 事件的显式接口实现必须使用事件访问器语法

event EventHandler IDbReference.DbRefEvent; 如果按照以上的写法,会提示错误: 事件的显式接口实现必须使用事件访问器语法 需要修改为一下这种写法 private EventHandler DbRefEvent;        event EventHandler IDbReference.DbRefEvent        {            add            {                DbRefEvent += value; 

枚举例题源码,反射例题源码,模板与装饰器模式例题源码

枚举例题:package cn.itcast_02; /* * 通过JDK5提供的枚举来做枚举类 */public enum Direction { FRONT, BEHIND, LEFT, RIGHT;} ---------------------------------------package cn.itcast_02; /* * 通过JDK5提供的枚举来做枚举类 */public enum Direction2 { FRONT("前"), BEHIND("后"

为其他对象提供一种代理以控制对这个对象的访问-代理模式

一.前言 在某些情况下,一个客户不想或者不能直接引用一个对 象,此时可以通过一个称之为“代理”的第三者来实现 间接引用.代理对象可以在客户端和目标对象之间起到 中介的作用,并且可以通过代理对象去掉客户不能看到 的内容和服务或者添加客户需要的额外服务. 通过引入一个新的对象来实现对真实对象的操作或者将新的对 象作为真实对象的一个替身,这种实现机制即 为代理模式,通过引入代理对象来间接访问一 个对象,这就是代理模式的模式动机. 在代理模式(Proxy Pattern)中,一个类代表另一个类的功能.这