@@@模式定义:
表示一个作用于某对象结构中的各元素的操作。它使你可以在不改变各元素的类的前提下

定义作用于这些元素的新操作。

@@@练习示例: 

扩展客户管理的功能

@@@示例代码:

\pattern\Customer.java

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

package pattern;

public abstract class Customer {
private String customerId;
private String name; public String getCustomerId() {
return customerId;
} public void setCustomerId(String customerId) {
this.customerId = customerId;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} /**
* 接受访问者的访问
* @param visitor 访问者对象
*/
public abstract void accept(Visitor visitor);
}

\pattern\Visitor.java

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

package pattern;

/**
* 访问者接口
*/
public interface Visitor {
/**
* 访问企业客户,相当于给企业客户添加访问者的功能
* @param ec 企业客户的对象
*/
public void visitEnterpriseCustomer(EnterpriseCustomer ec); /**
* 访问个人客户,相当于给个人客户添加访问者的功能
* @param pc 个人客户的对象
*/
public void visitPersonalCustomer(PersonalCustomer pc);
}

\pattern\EnterpriseCustomer.java

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

package pattern;

public class EnterpriseCustomer extends Customer {
private String linkman;
private String linkTelephone;
private String registerAddress; public String getLinkman() {
return linkman;
} public void setLinkman(String linkman) {
this.linkman = linkman;
} public String getLinkTelephone() {
return linkTelephone;
} public void setLinkTelephone(String linkTelephone) {
this.linkTelephone = linkTelephone;
} public String getRegisterAddress() {
return registerAddress;
} public void setRegisterAddress(String registerAddress) {
this.registerAddress = registerAddress;
} @Override
public void accept(Visitor visitor) {
// 回调访问者对象的相应方法
visitor.visitEnterpriseCustomer(this);
}
}

\pattern\PersonalCustomer.java

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

package pattern;

public class PersonalCustomer extends Customer {
private String telephone;
private String age; public String getTelephone() {
return telephone;
} public void setTelephone(String telephone) {
this.telephone = telephone;
} public String getAge() {
return age;
} public void setAge(String age) {
this.age = age;
} @Override
public void accept(Visitor visitor) {
// 回调访问者对象的相应方法
visitor.visitPersonalCustomer(this);
}
}

\pattern\ServiceRequestVisitor.java

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

package pattern;

/**
* 具体的访问者,实现客户提出服务请求的功能
*/
public class ServiceRequestVisitor implements Visitor {
@Override
public void visitEnterpriseCustomer(EnterpriseCustomer ec) {
// 企业客户提出的具体服务请求
System.out.println(ec.getName() + "企业提出服务请求");
} @Override
public void visitPersonalCustomer(PersonalCustomer pc) {
// 个人客户提出的具体服务请求
System.out.println("客户" + pc.getName() + "提出服务请求");
}
}

\pattern\PredilectionAnalyzeVisitor.java

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

package pattern;

/**
* 具体的访问者,实现对客户的偏好分析
*/
public class PredilectionAnalyzeVisitor implements Visitor {
@Override
public void visitEnterpriseCustomer(EnterpriseCustomer ec) {
// 根据以往购买的历史、潜在购买意向
// 以及客户所在行业的发展趋势、客户的发展预期等的分析
System.out.println("现在对企业客户" + ec.getName() + "进行产品偏好分析");
} @Override
public void visitPersonalCustomer(PersonalCustomer pc) {
System.out.println("现在对个人客户" + pc.getName() + "进行产品偏好分析");
}
}

\pattern\ObjectStructure.java

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

package pattern;

import java.util.ArrayList;
import java.util.Collection; public class ObjectStructure {
/**
* 要操作的客户集合
*/
private Collection<Customer> col = new ArrayList<Customer>(); /**
* 提供给客户端操作的高层接口,具体的功能由客户端传入的访问者决定
* @param visitor 客户端需要使用的访问者
*/
public void handleRequest(Visitor visitor) {
// 循环对象结构中的元素,接受访问
for (Customer cm : col) {
cm.accept(visitor);
}
} /**
* 组建对象结构,向对象结构中添加元素
* 不同的对象结构有不同的构建方式
* @param ele 加入到对象结构中的元素
*/
public void addElement(Customer ele) {
this.col.add(ele);
}
}

\user\Client.java

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

package user;

import pattern.Customer;
import pattern.EnterpriseCustomer;
import pattern.ObjectStructure;
import pattern.PersonalCustomer;
import pattern.PredilectionAnalyzeVisitor;
import pattern.ServiceRequestVisitor; public class Client {
public static void main(String[] args) {
// 创建ObjectStructure
ObjectStructure os = new ObjectStructure();
// 准备些测试数据,创建客户对象,并加入ObjectStructure
Customer cm1 = new EnterpriseCustomer();
cm1.setName("ABC集团");
os.addElement(cm1); Customer cm2 = new EnterpriseCustomer();
cm2.setName("CDE公司");
os.addElement(cm2); Customer cm3 = new PersonalCustomer();
cm3.setName("张三");
os.addElement(cm3); // 客户提出服务请求,传入服务请求的Visitor
ServiceRequestVisitor srVisitor =
new ServiceRequestVisitor();
os.handleRequest(srVisitor); // 要对客户进行偏好分析,传入偏好分析的Visitor
PredilectionAnalyzeVisitor paVisitor =
new PredilectionAnalyzeVisitor();
os.handleRequest(paVisitor);
}
}

@@@运行结果:

ABC集团企业提出服务请求

CDE公司企业提出服务请求

客户张三提出服务请求

现在对企业客户ABC集团进行产品偏好分析

现在对企业客户CDE公司进行产品偏好分析

现在对个人客户张三进行产品偏好分析

@@@模式的实现:

有一个调用回路,进行了两次分发。

@@@模式的优点:

好的扩展性;

好的复用性;

分离无关行为;

@@@模式的缺点:

对象结构变化很困难;

破环封装;

@@@模式的本质:

预留通路,回调实现。

@@@模式体现的设计原则:

NA

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

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

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

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

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

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

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

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

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

  5. 访问者模式(Visitor Pattern)——操作复杂对象结构

    模式概述 在软件开发中,可能会遇到操作复杂对象结构的场景,在该对象结构中存储了多个不同类型的对象信息,而且对同一对象结构中的元素的操作方式并不唯一,可能需要提供多种不同的处理方式,还有可能增加新的处理 ...

  6. 十一个行为模式之访问者模式(Visitor Pattern)

    定义: 提供一个作用于某对象结构(通常是一个对象集合)的操作的接口,使得在添加新的操作或者在添加新的元素时,不需要修改原有系统,就可以对各个对象进行操作. 结构图: Visitor:抽象访问者类,对元 ...

  7. C#设计模式——访问者模式(Visitor Pattern)

    一.概述由于需求的改变,某些类常常需要增加新的功能,但由于种种原因这些类层次必须保持稳定,不允许开发人员随意修改.对此,访问者模式可以在不更改类层次结构的前提下透明的为各个类动态添加新的功能.二.访问 ...

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

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

  9. 学习笔记——访问者模式Visitor

    访问者模式,通过Visitor的注入,为Element扩展了方法实现.虽然避免了Element不用修改即可修改,但却破坏了类的封装性,同时,一旦变更就需要增加子类,在子类方法中调用基类方法,然后再使用 ...

  10. 24访问者模式Visitor

    一.什么是访问者模式 Visitor模式也叫访问者模式,是行为模式之一 ,它分离对象的数据和行为,使用Visitor模式, 可以不修改已有类的情况下,增加新的操作. 二.访问者模式的应用示例 比如有一 ...

随机推荐

  1. 关于Apple设备私有的apple-touch-icon属性详解

    以前我们用过favicon在浏览器给网站进行身份标识,用法如下: <link href="http://image.feeliu.com/web/favicon.ico" r ...

  2. "The request sent by the client was syntactically incorrect ()"问题定位及解决:

    Spring MVC "The request sent by the client was syntactically incorrect ()"解决办法: 把spring日志级 ...

  3. 『重构--改善既有代码的设计』读书笔记----Change Value to Reference

    有时候你会认为某个对象应该是去全局唯一的,这就是引用(Reference)的概念.它代表当你在某个地点对他进行修改之后,那么所有共享他的对象都应该在再次访问他的时候得到相应的修改.而不会像值对象(Va ...

  4. 【原创】史上最全的Android开发环境搭建

    开始学习Android了 看着眼花缭乱的教程真心无奈...So  无耻的来了个大综合 自己充当了小白鼠.. (PS 若文章中链接失效 请留言反馈me会尽快修复) 开始的开始 java运行环境还是很必要 ...

  5. jquery 效果

    效果1.基本效果    1.1 show([speed,[easing],[fn]]) 如果元素本身是可见的,则不对其作任何改变.如果元素是隐藏的,则使其可见.        $("p&qu ...

  6. Chromium网页Frame Tree创建过程分析

         Chromium在加载一个网页之前,需要在Browser进程创建一个Frame Tree.Browser进程为网页创建了Frame Tree之后,再请求Render进程加载其内容.Frame ...

  7. Kafka源码分析-序列2 -Producer

    在上一篇,我们从使用方式和策略上,对消息队列做了一个宏观描述.从本篇开始,我们将深入到源码内部,仔细分析Kafka到底是如何实现一个分布式消息队列.我们的分析将从Producer端开始. 从Kafka ...

  8. js验证手机号码 ,昵称,密码

    手机号 /^[+]{0,1}(\d){1,3}[ ]?([-]?((\d)|[ ]){1,12})+$/ 传真~  /^(\d{3,4}-)?\d{7,8}$/ 邮箱 ^[a-z0-9]+([._\\ ...

  9. JavaScript学习心得(七)

    一 创建事件监听器 开发人员往往使用事件和元素组合来命名事件处理函数. 创建事件监听器方法: 嵌入式事件处理器即将JavaScript函数赋值给HTML元素属性(不推荐使用:污染HTML:无法应用渐进 ...

  10. php约瑟夫环

    <?php function popChar($str , $m , $current = 0){ $number = count($str); $num = 1; if(count($str) ...