`
sun201200204
  • 浏览: 303537 次
  • 性别: Icon_minigender_1
  • 来自: 深圳
社区版块
存档分类
最新评论

关于23种设计模式的有趣见解 --- VISITOR

    博客分类:
  • java
阅读更多
好久没发贴了。现在大家都在讨论设计模式,今天也来火一把:)
就把http://www.jdon.com上看到的有个《关于23种设计模式的有趣见解》解答一下,请大家拍砖。
先从VISITOR开始吧:

VISITOR—情人节到了,要给每个MM送一束鲜花和一张卡片,可是每个MM送的花都要针对她个人的特点,每张卡片也要根据个人的特点来挑,我一个人哪搞得清楚,还是找花店老板和礼品店老板做一下Visitor,让花店老板根据MM的特点选一束花,让礼品店老板也根据每个人特点选一张卡,这样就轻松多了;
       
访问者模式:访问者模式的目的是封装一些施加于某种数据结构元素之上的操作。一旦这些操作需要修改的话,接受这个操作的数据结构可以保持不变。访问者模式适用于数据结构相对未定的系统,它把数据结构和作用于结构上的操作之间的耦合解脱开,使得操作集合可以相对自由的演化。访问者模式使得增加新的操作变的很容易,就是增加一个新的访问者类。访问者模式将有关的行为集中到一个访问者对象中,而不是分散到一个个的节点类中。当使用访问者模式时,要将尽可能多的对象浏览逻辑放在访问者类中,而不是放到它的子类中。访问者模式可以跨过几个类的等级结构访问属于不同的等级结构的成员类。

先上代码:
先实现美女类,用四大美女来模拟。
package com.test.girl;

public interface Girl {
	void flow();
	void card();
}

package com.test.girl;

public class XiShi implements Girl {

	@Override
	public void card() {
		System.out.println("credit card");
	}

	@Override
	public void flow() {
		System.out.println("rose");
	}
}

package com.test.girl;

public class DiaoChan implements Girl {

	@Override
	public void card() {
		System.out.println("shop card");
	}

	@Override
	public void flow() {
		System.out.println("peony");
	}

}

package com.test.girl;

public class WangZhaojun implements Girl {

	@Override
	public void card() {
		System.out.println("king card");
	}

	@Override
	public void flow() {
		System.out.println("orchid");
	}
}

package com.test.girl;

public class YangYuhuan implements Girl {

	@Override
	public void card() {
		System.out.println("vip card");
	}

	@Override
	public void flow() {
		System.out.println("plum blossom");
	}
}

下面定义观察者:
package com.test.visitor;

public interface Visitor {
	void visit();
	void add(Object obj);
	void remove(Object obj);
}

这里只实现花店:
package com.test.visitor;

import java.util.ArrayList;
import java.util.List;

import com.test.girl.Girl;

public class Flowor implements Visitor {

	private List<Girl> girls = new ArrayList<Girl>();
	
	@Override
	public void visit() {
		for(Girl g:girls){
			g.flow();
		}
	}
	@Override
	public void add(Object g){
		girls.add((Girl)g);
	}
	@Override
	public void remove(Object g){
		girls.remove((Girl)g);
	}
}

写测试类:
package com.test.visitor;

import com.test.girl.DiaoChan;
import com.test.girl.Girl;
import com.test.girl.WangZhaojun;
import com.test.girl.XiShi;
import com.test.girl.YangYuhuan;

public class VisitorTest {

	/**
	 * @param args
	 */
	public static void main(String[] args) {
		Visitor v = new Flowor();
		Girl 西施 = new XiShi();
		Girl 貂蝉 = new DiaoChan();
		Girl 王昭君 = new WangZhaojun();
		Girl 杨玉环 = new YangYuhuan();
		v.add(西施);
		v.add(貂蝉);
		v.add(王昭君);
		v.add(杨玉环);
		
		v.visit();
		System.out.println("+++++++++++");
		v.remove(杨玉环);
		v.visit();
	}
}
分享到:
评论
5 楼 liuyizhang 2010-02-09  
前面观察者模式写的有点问题
4 楼 sun201200204 2010-02-02  
<p>这个模式凭着感觉写出来的,这个应该是观察者模式。写错了。<br>修正一下。<br>1.类图:(摘自:<a href="http://zh.wikipedia.org/wiki/%E8%AE%BF%E9%97%AE%E8%80%85%E6%A8%A1%E5%BC%8F">http://zh.wikipedia.org/wiki/%E8%AE%BF%E9%97%AE%E8%80%85%E6%A8%A1%E5%BC%8F</a>)<br><img src="http://dl.iteye.com/upload/picture/pic/54195/f2f3eef6-a588-3240-bd7e-78f23f2a52d3.png" alt="visitor" width="624" height="502"></p>
<p> </p>
<p>2.DEMO:</p>
<p> </p>
<p>元素角色:定义一个accept操作,它以一个访问者为参数。</p>
<pre name="code" class="java">package com.test.girl;

import com.test.visitor.Visitor;

public interface Girl {
void accept(Visitor visitor);
void flower();
void card();
}</pre>
<p> 下面是具体的元素角色:</p>
<pre name="code" class="java">package com.test.girl;

import com.test.visitor.Visitor;


public class DiaoChan implements Girl {

@Override
public void accept(Visitor visitor) {
visitor.visit(this);
}

/**
* 腊梅
*/
@Override
public void flower() {
System.out.println("winter sweet");
}

@Override
public void card() {
System.out.println("shopping card");
}

}</pre>
<p> </p>
<pre name="code" class="java">package com.test.girl;

import com.test.visitor.Visitor;

public class WangZhaojun implements Girl {

@Override
public void card() {
System.out.println("king card");
}

@Override
public void flower() {
System.out.println("orchid");
}


@Override
public void accept(Visitor visitor) {
visitor.visit(this);
}
}</pre>
<p> </p>
<pre name="code" class="java">package com.test.girl;

import com.test.visitor.Visitor;

public class XiShi implements Girl {

@Override
public void card() {
System.out.println("credit card");
}

@Override
public void flower() {
System.out.println("rose");
}

@Override
public void accept(Visitor visitor) {
visitor.visit(this);
}
}</pre>
<p> </p>
<pre name="code" class="java">package com.test.girl;

import com.test.visitor.Visitor;


public class YangYuhuan implements Girl {

@Override
public void card() {
System.out.println("vip card");
}

@Override
public void flower() {
System.out.println("plum blossom");
}

@Override
public void accept(Visitor visitor) {
visitor.visit(this);
}
}</pre>
<p> 访问者角色(Visitor):为该对象结构中具体元素角色声明一个访问操作接口。该操作接口的名字和参数标识了发送访问请求给具体访问者的具体元素角色。这样访问者就可以通过该元素角色的特定接口直接访问它。</p>
<pre name="code" class="java">package com.test.visitor;

import com.test.girl.DiaoChan;
import com.test.girl.WangZhaojun;
import com.test.girl.XiShi;
import com.test.girl.YangYuhuan;

public interface Visitor {
void visit(DiaoChan diaoChan);
void visit(WangZhaojun wangZhaojun);
void visit(XiShi xiShi);
void visit(YangYuhuan yangYuhuan);
}</pre>
<p> </p>
<p>下面是具体访问者:</p>
<pre name="code" class="java">package com.test.visitor;

import com.test.girl.DiaoChan;
import com.test.girl.WangZhaojun;
import com.test.girl.XiShi;
import com.test.girl.YangYuhuan;

/**
* record every girl's flower.
* @author Dave Li
*
*/
public class FlowerBoss implements Visitor {

@Override
public void visit(DiaoChan diaoChan) {
diaoChan.flower();
}

@Override
public void visit(WangZhaojun wangZhaojun) {
wangZhaojun.flower();
}

@Override
public void visit(XiShi xiShi) {
xiShi.flower();
}

@Override
public void visit(YangYuhuan yangYuhuan) {
yangYuhuan.flower();
}

}</pre>
<p> 对象结构角色(Object Structure):这是使用访问者模式必备的角色。它要具备以下特征:</p>
<p>      1)能枚举它的元素;</p>
<p>      2)可以提供一个高层的接口以允许该访问者访问它的元素;</p>
<p>      3)可以是一个复合(组合模式)或是一个集合,如一个列表或一个无序集合。</p>
<pre name="code" class="java">package com.test.visitor;

import com.test.girl.DiaoChan;
import com.test.girl.Girl;
import com.test.girl.WangZhaojun;
import com.test.girl.XiShi;
import com.test.girl.YangYuhuan;
/*
* 采购鲜花
*/
public class FlowerPurchase {

private Girl[] girls = {new DiaoChan(),
new WangZhaojun(),
new XiShi(),
new YangYuhuan()};

public void purchase(Visitor v){
for(Girl girl:girls){
girl.accept(v);
}
}
}</pre>
<p> </p>
<p>测试类:</p>
<pre name="code" class="java">package com.test.visitor;

public class Test {
public static void main(String[] args) {
FlowerPurchase purchase = new FlowerPurchase();
purchase.purchase(new FlowerBoss());
}
}</pre>
<p> </p>
<p>3.特点:</p>
<p>双重分配:</p>
<p>             purchase.purchase(new FlowerBoss());(给每个具体的角色分派一个具体观察者)。</p>
<p>             visitor.visit(this);具体访问者模式再根据参数的不同来选择方法来执行。</p>
<p> </p>
<p>在两个接口Visitor和Girl中,确保Girl很少变化,也就是说,确保不能老有新的Element元素类型加进来,可以变化的是访问者行为或操作,也就是Visitor的不同子类可以有多种,这样使用访问者模式最方便.</p>
<p>所以这个例子不太合适,花店的顾客是不断变化的,girl也是不断变化的。</p>
<p> </p>
<p>4,适用场合:</p>
<p>《设计模式》一书中给出了访问者模式适用的情况:<br><br>  1) 一个对象结构包含很多类对象,它们有不同的接口,而你想对这些对象实施一些依赖于其具体类的操作。<br><br>  2) 需要对一个对象结构中的对象进行很多不同的并且不相关的操作,而你想避免让这些操作“污染”这些对象的类。Visitor使得你可以将相关的操作集中起来定义在一个类中。<br><br>  3) 当该对象结构被很多应用共享时,用Visitor模式让每个应用仅包含需要用到的操作。<br><br>  4) 定义对象结构的类很少改变,但经常需要在此结构上定义新的操作。改变对象结构类需要重定义对所有访问者的接口,这可能需要很大的代价。如果对象结构类经常改变,那么可能还是在这些类中定义这些操作较好。</p>
3 楼 jashawn 2010-01-30  
这明显不是visitor...偏差太大了……你的visitor居然和你要访问的东西是聚合关系。
2 楼 joknm 2010-01-29  
有点适配器的味道。
1 楼 ahuango 2010-01-29  
从代码没看出Vistor 的真谛

相关推荐

    关于23种设计模式的有趣见解.docx

    "关于23种设计模式的有趣见解" 在软件设计中,设计模式扮演着非常重要的角色,它们提供了一些已经被证实的、已经被人所熟悉的解决方案,可以帮助开发者更快、更好、更可靠地开发软件。下面我们将对23种设计模式进行...

    关于Java 23种设计模式的有趣见解.docx

    Java 23种设计模式是软件开发中非常重要的概念,它们是解决常见设计问题的成熟解决方案,被广泛应用于各种软件架构中。以下是这些设计模式的简要解释: 1. **工厂模式**:这是一种创建型模式,它提供了一种创建对象...

    神经元细胞核检测数据集.zip

    数据集介绍:神经元细胞核检测数据集 一、基础信息 数据集名称:神经元细胞核检测数据集 图片数量: - 训练集:16,353张 - 测试集:963张 分类类别: - Neuron(神经元细胞核):中枢神经系统的基本功能单位,检测其形态特征对神经科学研究具有重要意义。 标注格式: - YOLO格式,包含边界框坐标及类别标签,适用于目标检测任务 - 数据来源于显微镜成像,覆盖多种细胞分布形态和成像条件 二、适用场景 神经科学研究: 支持构建神经元定位分析工具,助力脑科学研究和神经系统疾病机理探索 医学影像分析: 适用于开发自动化细胞核检测系统,辅助病理诊断和细胞计数任务 AI辅助诊断工具开发: 可用于训练检测神经元退行性病变的模型,支持阿尔茨海默症等神经疾病的早期筛查 生物教育及研究: 提供标准化的神经元检测数据,适用于高校生物学实验室和科研机构的教学实验 三、数据集优势 大规模训练样本: 包含超1.6万张训练图像,充分覆盖细胞核的多样分布状态,支持模型深度学习 精准定位标注: 所有标注框均严格贴合细胞核边缘,确保目标检测模型的训练精度 任务适配性强: 原生YOLO格式可直接应用于主流检测框架(YOLOv5/v7/v8等),支持快速模型迭代 生物学特性突出: 专注神经元细胞核的形态特征,包含密集分布、重叠细胞等真实生物场景样本 跨领域应用潜力: 检测结果可延伸应用于细胞计数、病理分析、药物研发等多个生物医学领域

    剪切散斑干涉条纹图像处理技术研究进展.pdf

    剪切散斑干涉条纹图像处理技术研究进展.pdf

    网络规划设计师网络理论基础(1-6章).pdf

    软考初级程序员相关文档

    ATB2012-75011-T00-射频组件-中文数据手册.pdf

    ATB2012-75011-T00-射频组件-中文数据手册

    光伏储能系统三相PQ恒功率并网控制策略仿真研究——基于双闭环控制与MPPT算法的优化实践 MATLAB仿真 光伏储能三相PQ恒功率并网控制仿真:网侧PQ恒控、储能双闭环控制策略及光伏Boost研究

    内容概要:本文详细介绍了光伏储能系统中三相PQ恒功率并网控制策略的仿真研究。主要内容涵盖网侧PQ恒功率控制、储能系统的双闭环控制策略以及光伏Boost模型的构建。网侧控制采用PQ恒功率控制,确保系统在各种负载条件下维持恒定功率输出,减少电能损失和电网能耗。储能控制部分,通过直流母线电压外环和电池电流内环的双闭环控制策略,实现了对系统输出电压和电池充放电电流的精确控制。光伏Boost模型则基于经典MPPT算法(如扰动观察法),确保在功率等级相似情况下仅需调整光伏模块即可满足需求。文中还展示了使用MATLAB等工具进行仿真的示例代码,评估不同控制策略的效果。 适合人群:从事电力系统、新能源技术和自动化控制领域的研究人员和技术人员。 使用场景及目标:适用于希望深入了解光伏储能系统控制策略及其仿真方法的专业人士,帮助他们掌握最新的技术进展和应用实例。 其他说明:文章引用了相关文献,提供了丰富的理论基础和实践经验,有助于进一步研究和探讨光伏储能技术的发展趋势和应用前景。

    毕业设计-分享送红包 3.0.1-整站商业源码.zip

    毕业设计-分享送红包 3.0.1-整站商业源码.zip

    毕业设计-互联网加共享农业V1.3.6 小程序前端+后端-整站商业源码.zip

    毕业设计-互联网加共享农业V1.3.6 小程序前端+后端-整站商业源码.zip

    基于Matlab Simulink的双馈风机风电场调频研究:虚拟惯性惯量与下垂控制技术

    内容概要:本文探讨了在Matlab/Simulink环境下,针对双馈风机风电场的一次调频方法,特别是虚拟惯性惯量控制和下垂控制的应用。文中介绍了这两种控制策略的具体实现方式及其在三机九节点系统中的应用,同时讨论了同步机、火电和水电机组的调频机制。此外,文章强调了Phasor模型在提高仿真速度方面的作用,使得仿真时间缩短至仅需20秒。 适合人群:从事风力发电、电力系统自动化及相关领域的研究人员和技术人员。 使用场景及目标:适用于希望深入了解风电调频技术的研究人员,旨在提供一种高效、快速的仿真工具,以便更好地理解和优化风电场的调频性能。 其他说明:文章不仅提供了理论解释,还包括具体的Matlab/Simulink代码片段,便于读者实际操作和验证。

    MATLAB Simulink中PID控制器用于智能建筑温度控制的仿真研究 PID控制器

    内容概要:本文介绍了PID控制器在智能建筑温度控制中的应用,特别是通过MATLAB的Simulink工具进行仿真的过程。首先阐述了PID控制器的基本原理及其优点,接着详细描述了如何在Simulink中建立PID控制模型并调整相关参数,最后展示了具体的MATLAB代码示例以及仿真结果。文章强调了PID控制器在提高温度控制精度方面的重要性和广泛应用前景。 适合人群:对自动化控制理论感兴趣的学生和技术爱好者,尤其是那些希望深入了解PID控制器工作原理及其在实际工程中应用的人群。 使用场景及目标:适用于想要学习如何使用MATLAB/Simulink进行控制系统仿真的初学者或者有一定经验的研发人员,旨在帮助他们掌握PID控制器的设计与实现技巧。 其他说明:文中提供的示例代码可以帮助读者更快地上手操作,同时鼓励读者尝试不同的参数配置以优化控制性能。此外,还提到了PID控制器在未来可能的发展方向和应用场景。

    【空间智能领域】基于3D视觉的多应用场景分析:自动驾驶、3D生成、具身智能及扩展现实(XR)技术发展趋势报告

    内容概要:报告详细分析了空间智能的发展现状与未来趋势,涵盖自动驾驶、3D生成、具身智能、扩展现实(XR)和世界模型五大领域。自动驾驶凭借庞大的车队数据积累和成熟的数据闭环机制,成为目前最成熟的空间智能应用,正逐步从模仿学习转向强化学习。3D生成技术处于快速发展阶段,主要瓶颈在于寻找具有良好扩展性的3D数据表征方式。具身智能虽然潜力巨大,但整体成熟度较低,数据积累、算法和硬件方面均处于早期探索阶段。XR作为新的信息交互方式,其硬件基础逐渐成熟,未来将推动更多3D原生内容和应用生态的繁荣。世界模型则是空间智能发展的终极目标,它通过构建对现实世界的内部表征,实现对未来状态的预测和行动后果的推理。 适合人群:对空间智能领域感兴趣的科技从业者、研究人员、投资者及相关政策制定者。 使用场景及目标:①了解空间智能各细分领域的技术进展、挑战和发展趋势;②评估投资机会和技术合作方向;③为政策制定提供参考依据。 其他说明:报告强调了数据体系成熟度是观察空间智能进展的关键指标,包括数据积累、数据构成、数据分布和数据闭环四部分。此外,报告还指出,随着3D和物理AI数据体系的进一步成熟,空间智能将迎来爆发式增长。

    基于粒子群优化算法的永磁同步电机(PMSM)参数辨识:高效智能优化方法与实验研究

    内容概要:本文详细介绍了基于粒子群优化算法(PSO)的永磁同步电机(PMSM)参数辨识方法。文章从引言部分阐述了PMSM的重要性和参数辨识的需求出发,逐步深入到具体的算法流程,包括粒子群的初始化、速度和位置的更新及其边界处理、自适应变异、约束条件判断以及适应度计算与比较。通过多次迭代,最终确定最优的电机参数组合。文中还讨论了实际应用中的调整技巧和未来的研究方向。 适合人群:从事电机控制、自动化工程及相关领域的研究人员和技术人员。 使用场景及目标:适用于需要对永磁同步电机进行高精度参数辨识的场合,如工业自动化设备、电动汽车等领域。目标是提升电机控制系统的性能,确保系统稳定运行。 其他说明:本文不仅提供了理论依据,还结合了大量实验数据验证了该方法的有效性,为后续研究奠定了坚实的基础。

    多环境动物及人类活动目标检测数据集.zip

    数据集介绍:多环境动物及人类活动目标检测数据集 一、基础信息 数据集名称:多环境动物及人类活动目标检测数据集 图片数量: - 训练集:12,599张图片 - 验证集:1,214张图片 - 测试集:607张图片 总计:14,420张图片 分类类别: - bear(熊): 森林生态系统的顶级掠食者 - bird(鸟类): 涵盖多种飞行及陆栖鸟类 - cougar(美洲狮): 山地生态关键物种 - person(人类): 自然环境与人类活动交互场景 - truck(卡车): 工业及运输场景的车辆目标 - ungulate(有蹄类动物): 包括鹿、羊等草食性哺乳动物 - wolf(狼): 群体性捕食动物代表 标注格式: YOLO格式标注,包含归一化坐标的边界框及类别标签,可直接适配YOLOv5/v7/v8等主流检测框架。 数据特性: 涵盖航拍、地面监控等多视角数据,包含昼夜不同光照条件及复杂背景场景。 二、适用场景 野生动物保护监测: 支持构建自动识别森林/草原生态系统中濒危物种的监测系统,用于种群数量统计和栖息地研究。 农业与畜牧业管理: 检测农场周边的捕食动物(如狼、美洲狮),及时预警牲畜安全风险。 智能交通系统: 识别道路周边野生动物与运输车辆,为自动驾驶系统提供碰撞预警数据支持。 生态研究数据库: 提供7类典型生物与人类活动目标的标注数据,支撑生物多样性分析与人类活动影响研究。 安防监控增强: 适用于自然保护区监控系统,同时检测可疑人员(person)与车辆(truck)的非法闯入。 三、数据集优势 多场景覆盖: 包含森林、公路、山地等多类型场景,覆盖从独居动物(cougar)到群体生物(wolf)的检测需求。 类别平衡设计: 7个类别经专业数据采样,避免长尾分布问题,包含: - 3类哺乳动物捕食者(bear/cougar/wolf) - 2类环境指示物种(bird/ung

    基于实体知识推理的端到端任务型对话.pdf

    基于实体知识推理的端到端任务型对话.pdf

    SSM框架下的酒店管理系统的源代码及数据库文件(适用于毕设)

    基于SSM的酒店管理系统源码+数据库文件.zip,该项目已高分通过。适用于计算机专业学生毕设及Java学习者实战练习,也可用于课程设计或期末大作业。包含项目源码、数据库脚本、软件工具及说明文档等,可直接使用。后台管理功能包括:会员信息管理(显示和删除)、客房信息管理(添加/删除客房类型和客房,编辑客房信息,未实现评论管理)、预订信息管理和入住信息管理(添加入住信息,结账后删除)。用户端主要功能有登录注册、客房预订及查看/编写评论。。内容来源于网络分享,如有侵权请联系我删除。

    毕业设计-灵石AI识别大全V3.0.0 小程序前端+后端-整站商业源码.zip

    毕业设计-灵石AI识别大全V3.0.0 小程序前端+后端-整站商业源码.zip

    CTF-Misc应用:图片隐写技术与实战项目解析

    CTF(Capture The Flag)竞赛中的Misc(杂项)类别题目涉及多种技术领域,包括隐写术、编码、取证、流量分析等。其中,图片隐写是CTF-Misc中常见且重要的题型之一。本文将重点介绍CTF-Misc中图片隐写技术的学习资料、操作应用以及实战项目。CTF-Misc中的图片隐写技术是竞赛中的重要题型。通过学习图片隐写的原理、操作应用以及实战项目,可以提升在CTF竞赛中的解题能力。掌握常见的隐写工具,并结合实战案例进行练习,是提高CTF-MISC技能的有效方法。

    网络规划设计师-英语题汇总.pdf

    软考初级程序员相关文档

    毕业设计-仿花生日记官网源码-整站商业源码.zip

    毕业设计-仿花生日记官网源码-整站商业源码.zip

Global site tag (gtag.js) - Google Analytics