访问者模式-Visitor

Posted LionheartCGJ

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了访问者模式-Visitor相关的知识,希望对你有一定的参考价值。

访问者模式:表示作用于某对象结构的个元素的操作.它使你在不改变各元素的类的前提下定义作用于这些元素的新操作.

访问者模式的适用场景:有比较稳定的数据结构,又有易于变化的算法的话,使用反复问这模式就是比较合适的,因为访问者模式使得算法操作的增加变得容易.

访问者模式的优缺点:

  • 优点:增加新的操作容易,因为增加新的操作就意味着增加一个新的访问者.访问者模式将有关的行为集中到一个访问者对象中.
  • 缺点:访问者模式使得增加新的数据结构变得苦难了.

访问者模式结构图:

代码实现:

 1 package com.cgj.pattern.visitor;
 2 
 3 /**
 4  * Visitor接口
 5  */
 6 public interface Action {
 7 
 8     // 得到男人结论或反应
 9     public abstract void getManConclusion(Man concreteElement);
10     
11     // 得到女人的结论或反应
12     public abstract void getWomanConclusion(Woman concreteElement);
13 }
 1 package com.cgj.pattern.visitor;
 2 
 3 /**
 4  * Element接口:定义一个访问的方法,它以一个访问者为参数
 5  */
 6 public interface Person {
 7 
 8     // 他是用来获得Visitor对象的
 9     public abstract void accept(Action visitor);
10 }
 1 package com.cgj.pattern.visitor;
 2 
 3 /**
 4  * 具体的Element类
 5  */
 6 public class Man implements Person {
 7 
 8     // visitor给出访问的结果
 9     @Override
10     public void accept(Action visitor) {
11         visitor.getManConclusion(this);
12     }
13 
14 }
 1 package com.cgj.pattern.visitor;
 2 
 3 /**
 4  * 具体的Element类
 5  */
 6 public class Woman implements Person {
 7 
 8     // visitor给出访问的结果
 9     @Override
10     public void accept(Action visitor) {
11         visitor.getWomanConclusion(this);
12     }
13 
14 }
 1 package com.cgj.pattern.visitor;
 2 
 3 /**
 4  * 具体的访问者,实现每个由Visitor声明的操作.
 5  * 每个操作实现算法的一部分,而该算法片段乃是对应于结构中对象的类.
 6  */
 7 public class Success implements Action {
 8 
 9     @Override
10     public void getManConclusion(Man concreteElement) {
11         System.out.println("男人成功时,背后多半有一个伟大的女人.");
12 
13     }
14 
15     @Override
16     public void getWomanConclusion(Woman concreteElement) {
17         System.out.println("女人成功时,背后大多有一个不成功的男人.");
18 
19     }
20 
21 }
 1 package com.cgj.pattern.visitor;
 2 
 3 /**
 4  * 具体的访问者,实现每个由Visitor声明的操作.
 5  * 每个操作实现算法的一部分,而该算法片段乃是对应于结构中对象的类.
 6  */
 7 public class Failing implements Action {
 8 
 9     @Override
10     public void getManConclusion(Man concreteElement) {
11         System.out.println("男人失败时,闷头喝酒谁也不用劝.");
12 
13     }
14 
15     @Override
16     public void getWomanConclusion(Woman concreteElement) {
17         System.out.println("女人失败时,眼泪汪汪,谁也劝不了.");
18 
19     }
20 
21 }
 1 package com.cgj.pattern.visitor;
 2 
 3 /**
 4  * 具体的访问者,实现每个由Visitor声明的操作.
 5  * 每个操作实现算法的一部分,而该算法片段乃是对应于结构中对象的类.
 6  */
 7 public class Amativeness implements Action {
 8 
 9     @Override
10     public void getManConclusion(Man concreteElement) {
11         System.out.println("男人恋爱时,凡是不懂也要装懂.");
12 
13     }
14 
15     @Override
16     public void getWomanConclusion(Woman concreteElement) {
17         System.out.println("女人恋爱时,遇事懂也装作不懂.");
18 
19     }
20 
21 }
 1 package com.cgj.pattern.visitor;
 2 
 3 import java.util.ArrayList;
 4 import java.util.List;
 5 
 6 /**
 7  * 能枚举它的元素,可以提供一个高层的接口以允许访问者访问他的元素.
 8  */
 9 public class ObjectStructure {
10 
11     private List<Person> elements = new ArrayList<Person>();
12 
13     public boolean add(Person element) {
14         return elements.add(element);
15     }
16 
17     public boolean detach(Person element) {
18         return elements.remove(element);
19     }
20 
21     // 枚举所有元素
22     public void display(Action visitor) {
23         for (Person element : elements) {
24             element.accept(visitor);
25         }
26     }
27 }
 1 package com.cgj.pattern.visitor;
 2 
 3 /**
 4  * 首先在display函数中将具体的状态传递给Man类完成第一次分派,
 5  * 然后Man调用作为参数的状态类中的getManConslusion函数同时将自身
 6  * 作为参数传递进去,这便完成了第二次分派.
 7  */
 8 public class Test {
 9 
10     public static void main(String[] args) {
11         ObjectStructure structure = new ObjectStructure();
12 
13         structure.add(new Man());
14         structure.add(new Woman());
15 
16         System.out.println("成功时的反应");
17         structure.display(new Success());
18 
19         System.out.println("失败时的反应");
20         structure.display(new Failing());
21 
22         System.out.println("恋爱时的反应");
23         structure.display(new Amativeness());
24     }
25 
26 }

(本随笔参考了程杰老师的<<大话设计模式>>)

以上是关于访问者模式-Visitor的主要内容,如果未能解决你的问题,请参考以下文章

访问者模式(Visitor Pattern)

24访问者模式Visitor

Visitor模式

设计模式之二十四:訪问者模式(Visitor)

访问者模式(Visitor)

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