访问者模式是一种将数据操作和数据结构分离的设计模式,可以说是面向数据密集型的一种设计方式,数据的结构相对稳定,有明显的分层和分类,而对数据对象的相关操作进行分组、分析等二次加工,这些操作都是由访问者来执行的,而不是将这些放到被访问的数据对象中,方便了操作方法的扩展。

作用

封装一些作用于某种数据结构中的各元素的操作,它可以在不改变这个数据结构的前提下定义作用于这些元素的新的操作。

类视图

实现

访问者模式的关键实现是在Element中的accept函数,该函数传入visitor,并在函数内调用visitor的针对该对象的方法,访问者调用元素类中的方法,又回到访问类中进行调用的方式叫做双重分派。

class Person
// 游乐设施
class Facility
{
public:
Facility():m_ncost_money(0), m_ncost_time(0){}
virtual void accept( Person*) =0;
virtual int SpendMoney()=0;
virtual int SpendTime()=0;
protected:
int m_ncost_money;
int m_ncost_time;
}; //摩天轮
class FerrisWheel : public Facility
{
public:
FerrisWheel():m_ncost_money(10), m_ncost_time(15){}
void accept( Person* persion)
{
persion->play(this);
}
int SpendMoney(){ return m_ncost_time;}
int SpendTime(){return m_ncost_money;}
};
//碰碰车
class BumperCar : public Facility
{
public:
BumperCar():m_ncost_money(30), m_ncost_time(10){}
void accept( Person* persion)
{
persion->play(this);
}
int SpendMoney(){ return m_ncost_time;}
int SpendTime(){return m_ncost_money;}
};
//过山车
class RollerCoaster : public Facility
{
public:
RollerCoaster():m_ncost_money(100), m_ncost_time(20){}
void accept( Person* persion)
{
persion->play(this);
}
int SpendMoney(){ return m_ncost_time;}
int SpendTime(){return m_ncost_money;}
}; class Person
{
public:
Person() : m_nToTalMoney(0),m_nToTalTime(0){}
void Play(FerrisWheel*);
void Play(BumperCar*);
void Play(FerrisWheel*);
public:
int GetTotalMoney()
{
return m_nToTalMoney;
}
int GetTotalTime()
{
return m_nToTalTime;
}
protected:
int m_nToTalMoney;
int m_nToTalTime; } class Adult : public Person
{
public:
void Play(FerrisWheel* ferriswheel)
{
int nMoney = ferriswheel->SpendMoney();
m_ncost_money+=nMoney;
int nTime = ferriswheel->SpendTime();
m_nToTalTime += nTime;
}
void Play(BumperCar* bumpercar)
{
int nMoney = BumperCar->SpendMoney();
m_ncost_money+=nMoney;
int nTime = BumperCar->SpendTime();
m_nToTalTime += nTime;
}
void Play(RollerCoaster* rollercoaster)
{
int nMoney = RollerCoaster->SpendMoney();
m_ncost_money+=nMoney;
int nTime = RollerCoaster->SpendTime();
m_nToTalTime += nTime;
} };
//儿童所有花费半价
class Childen : public Person
{
public:
void Play(FerrisWheel* ferriswheel)
{
int nMoney = ferriswheel->SpendMoney()/2;
m_ncost_money+=nMoney;
int nTime = ferriswheel->SpendTime();
m_nToTalTime += nTime;
}
void Play(BumperCar* bumpercar)
{
int nMoney = BumperCar->SpendMoney()/2;
m_ncost_money+=nMoney;
int nTime = BumperCar->SpendTime();
m_nToTalTime += nTime;
}
void Play(RollerCoaster* rollercoaster)
{
int nMoney = RollerCoaster->SpendMoney()/2;
m_ncost_money+=nMoney;
int nTime = RollerCoaster->SpendTime();
m_nToTalTime += nTime;
}
}; int main()
{
FerrisWheel fw;
BumperCar bc;
RollerCoaster rc; Childen son;
Adult mather;
//儿子玩了所有项目
son.play(fw);
son.play(bc);
son.play(rc);
//可怜的妈妈只陪儿子玩了一个过山车
mother.play(rc); int nSonCostMoney = son.GetTotalMoney();
int nSonCostTime = son.getTotalTime();
int nMotherCostMoney = mother.GetTotalMoney();
int nMotherCostTime = mother.getTotalTime(); cout<< "Son spend money :" << nSonCostMoney << " spend time: "<< nSonCostTime; << endl;
cout<< "Mother spend money :" << nMotherCostMoney << " Mother time: "<< nMotherCostTime; << endl; }

访问者模式的主要问题是因为每个访问者需要有对应的方法来处理每一种可能的具体数据,,那么一旦实现了访问者模式,其具体类的数量和类型就不能轻易被改变。

应用场景

  1. 对象结构比较稳定,但经常需要在此对象结构上定义新的操作。
  2. 需要对一个对象结构中的对象进行很多不同的且不相关的操作,而需要避免这些操作“污染”这些对象的类,也不希望在增加新操作时修改这些类。

设计模式之访问者模式(Visitor )的更多相关文章

  1. 乐在其中设计模式(C#) - 访问者模式(Visitor Pattern)

    原文:乐在其中设计模式(C#) - 访问者模式(Visitor Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 访问者模式(Visitor Pattern) 作者:webabc ...

  2. 二十四种设计模式:访问者模式(Visitor Pattern)

    访问者模式(Visitor Pattern) 介绍表示一个作用于某对象结构中的各元素的操作.它使你可以在不改变各元素的类的前提下定义作用于这些元素的新操作. 示例有一个Message实体类,某些对象对 ...

  3. [设计模式] 23 访问者模式 visitor Pattern

    在GOF的<设计模式:可复用面向对象软件的基础>一书中对访问者模式是这样说的:表示一个作用于某对象结构中的各元素的操作.它使你可以在不改变各元素的类的前提下定义作用于这些元素的新操作.访问 ...

  4. 设计模式(17) 访问者模式(VISITOR) C++实现

    意图: 表示一个作用于某对象结构的各元素的操作.它使你可以再不改变各元素的类的前提下定义作用于这些元素的新操作. 动机: 之前在学校的最后一个小项目就是做一个编译器,当时使用的就是访问者模式. 在静态 ...

  5. 【设计模式】—— 访问者模式Visitor

    前言:[模式总览]——————————by xingoo 模式意图 对于某个对象或者一组对象,不同的访问者,产生的结果不同,执行操作也不同.此时,就是访问者模式的典型应用了. 应用场景 1 不同的子类 ...

  6. 行为型设计模式之访问者模式(Visitor)

    结构 意图 表示一个作用于某对象结构中的各元素的操作.它使你可以在不改变各元素的类的前提下定义作用于这些元素的新操作. 适用性 一个对象结构包含很多类对象,它们有不同的接口,而你想对这些对象实施一些依 ...

  7. 设计模式 ( 二十 ) 访问者模式Visitor(对象行为型)

    设计模式 ( 二十 ) 访问者模式Visitor(对象行为型) 1.概述 在软件开发过程中,对于系统中的某些对象,它们存储在同一个集合collection中,且具有不同的类型,而且对于该集合中的对象, ...

  8. 访问者模式 Visitor 行为型 设计模式(二十七)

    访问者模式 Visitor    <侠客行>是当代作家金庸创作的长篇武侠小说,新版电视剧<侠客行>中,开篇有一段独白:  “茫茫海外,传说有座侠客岛,岛上赏善罚恶二使,每隔十年 ...

  9. 设计模式:访问者(Visitor)模式

    设计模式:访问者(Visitor)模式 一.前言    什么叫做访问,如果大家学过数据结构,对于这点就很清晰了,遍历就是访问的一般形式,单独读取一个元素进行相应的处理也叫作访问,读取到想要查看的内容+ ...

  10. 北风设计模式课程---访问者模式(Visitor)

    北风设计模式课程---访问者模式(Visitor) 一.总结 一句话总结: 设计模式是日常问题的经验总结方案,所以学好设计模式对日常出现的问题可以有很好的解决. 访问者设计模式有点神似 抽象工厂模式, ...

随机推荐

  1. 【C#】 使用Gsof.Native 动态调用 C动态库

    [C#] 使用Gsof.Native 动态调用 C动态库 一.背景 使用C# 开发客户端时候,我们经常会调用一些标准的动态库或是C的类库.虽然C# 提供的PInvoke的方式,但因为使用的场景的多变, ...

  2. 2.第一个ASP.NET MVC 5.0应用程序

    大家好,上一篇对ASP.NET MVC 有了一个基本的认识之后,这一篇,我们来看下怎么从头到尾创建一个ASP.NET MVC 应用程序吧.[PS:返回上一篇文章:1.开始学习ASP.NET MVC] ...

  3. Kaldi如何准备自己的数据

    Introduction 跑完kaldi的一些脚本例子,你可能想要自己用Kaldi跑自己的数据集.这里将会阐述如何准备好数据. run.sh较上的部分是有关数据准备的,通常local与数据集相关. 例 ...

  4. Rgb2Gray

    GPU上运行的函数又称为Kernel,用__global__修饰 调用Kernel函数时,用FunctionCall<<<block_shape, thread_shape, int ...

  5. 从零开始的程序逆向之路 第一章——认识OD(Ollydbg)以及常用汇编扫盲

    作者:Crazyman_Army 原文来自:https://bbs.ichunqiu.com/thread-43041-1-1.html 0×00 序言: 1.自从上次笔者调戏完盗取文件密码大黑客后, ...

  6. CentOS第一次安装MySQL的完整步骤

    文章来自:http://www.jianshu.com/p/4a41a6df19a6,我自己调整了下 1.官方安装文档 http://dev.mysql.com/doc/mysql-yum-repo- ...

  7. Java高级开发必会的50个性能优化细节

    在JAVA程序中,性能问题的大部分原因并不在于JAVA语言,而是程序本身.养成良好的编码习惯非常重要,能够显著地提升程序性能. 1. 尽量在合适的场合使用单例 使用单例可以减轻加载的负担,缩短加载的时 ...

  8. 小鬼难缠--python小bug备忘

    今天编译pyhon做人脸识别,遇到几个问题,做个记录吧. 编译报错: File "harrClassifier.py", line 17, in <module> fl ...

  9. Linux - 查看文件信息的三个命令

    ls命令 - list directory contents 显示文件详细信息:ls -l <file name> file命令 - determine file type determi ...

  10. centos7配置apache服务

    首先写下基本的步骤: 1.环境准备:关闭防火墙(不关闭无法访问,我这里只是简单的配置,实际部署项目应该会有具体的设置),关闭selinux(试过,不关闭也没事,一般都关闭) 配置 ip 2.安装软件包 ...