1.访问者模式的介绍
2.访问者模式的简单例子
访问者模式的介绍,本人本来打算用自己组织的语言写的,但在网上能找到一堆,有些人写得非常详细了,感觉比自己的表达还要好,故就不重新自己敲键盘了。下面关于访问者模式的介绍,主要来源http://www.cnblogs.com/java-my-life/archive/2012/06/14/2545381.html(这家伙的来源又是《JAVA与模式》,呵呵)。本文为什么不属于转载呢?呵呵,因为后面还有一个比较有实际意义的一个简单应用例子:Html页面按钮的权限处理。
1.访问者模式的介绍 访问者模式的结构访问者模式适用于数据结构相对未定的系统,它把数据结构和作用于结构上的操作之间的耦合解脱开,使得操作集合可以相对自由地演化。访问者模式的简略图如下所示: 数据结构的每一个节点都可以接受一个访问者的调用,此节点向访问者对象传入节点对象,而访问者对象则反过来执行节点对象的操作。这样的过程叫做“双重分派”。节点调用访问者,将它自己传入,访问者则将某算法针对此节点执行。访问者模式的示意性类图如下所示: 访问者模式涉及到的角色如下: ● 抽象访问者(Visitor)角色:声明了一个或者多个方法操作,形成所有的具体访问者角色必须实现的接口。 ● 具体访问者(ConcreteVisitor)角色:实现抽象访问者所声明的接口,也就是抽象访问者所声明的各个访问操作。 ● 抽象节点(Node)角色:声明一个接受操作,接受一个访问者对象作为一个参数。 ● 具体节点(ConcreteNode)角色:实现了抽象节点所规定的接受操作。 ● 结构对象(ObjectStructure)角色:有如下的责任,可以遍历结构中的所有元素;如果需要,提供一个高层次的接口让访问者对象可以访问每一个元素;如果需要,可以设计成一个复合对象或者一个聚集,如List或Set。
抽象节点角色
|
访问者模式的优点● 好的扩展性 能够在不修改对象结构中的元素的情况下,为对象结构中的元素添加新的功能。 ● 好的复用性 可以通过访问者来定义整个对象结构通用的功能,从而提高复用程度。 ● 分离无关行为 可以通过访问者来分离无关的行为,把相关的行为封装在一起,构成一个访问者,这样每一个访问者的功能都比较单一。 访问者模式的缺点● 对象结构变化很困难 不适用于对象结构中的类经常变化的情况,因为对象结构发生了改变,访问者的接口和访问者的实现都要发生相应的改变,代价太高。 ● 破坏封装 访问者模式通常需要对象结构开放内部数据给访问者和ObjectStructrue,这破坏了对象的封装性。 |
2.访问者模式的应用例子(按钮级别的权限判断)初步接触设计模式最痛苦的就是一些教程对设计模式的概念长篇大论,然后随便贴个简单例子的源码出来(例如上面,呵呵),没有举一些实际开发中哪些场景会使用到(对于初学者来说,更希望看到一些有意义的场景例子)。
需求:html页面的按钮需要根据用户的权限进行判断,是否显示或者隐藏或者删除(总之就是用户如果没有操作那个按钮的权限,页面上就不要让用户看见)。
html其实也是一颗树,拥有不同的节点。为了解析html页面,借用了htmlparser工具。这个可以在网上下载。通过htmlparser可以很方便的获得html的节点,然后自己自定义一个NodeVisitor,访问节点,并对特殊的节点(被标识,需要判断权限的按钮等节点)进行加工,比如delete或者display等操作。
假如有这样一个页面,上面有4个按钮,查询,添加,修改,删除,其中添加,修改,删除按钮都需根据用户的权限进行动态显示。页面初始源码及效果图如下(需权限判断的按钮,使用sys_opt="xxx"表示,xxx表示按钮的功能,如果remove)
原始的html页面源码及效果图,如下。
UserPurview.java模拟用户拥有权限并判断
下面是客户端测试类。
看看处理好的html源码及效果图。 |
遍历body区域内的所有节点,被封装在org.htmlparser.tags.CompositeTag.accept(NodeVisitor visitor)中。下面看看它的源码
|