Clark To Do The blog of Clark

Java设计模式:访问者模式

注:本文为译文,原文出处java-design-patterns-in-stories

访问者模式是一种被广泛应用在编译器的转换器中的设计模式, 比如Eclipse JDT AST转换器.

基本上, 访问者模式包含两个接口 - Visitor与Element.

访问者模式故事

设想一个访问者初次来到纽约. 他想要参观城市比国并且这个城市也接受了它的到访. 一旦访问者开始参观, 就会自动的参观所有地方, 并且他想去博物馆时不需要调用某个方法. 旅行就是一个打包的交易!

访问者模式类图

visitor-pattern-class-diagram

访问者模式步骤

这个图展示了参观的步骤.

  1. 创建参观者FirstTimeVisitor和元素角色City
  2. 程序以”City接收一个访问者”开始
  3. City中的accept方法定义: 使访问者去参观
  4. 被接受的访问者调用它重写的方法visit来参观City

访问者模式Java代码

import java.util.ArrayList;

interface Visitor {
  public void visit(City city);
  public void visit(Museum museum);
  public void visit(Park park);
}

class FirstTimeVisitor implements Visitor {

  @Override
  public void visit(City city) {
    System.out.println("I'm visiting the city!");
  }

  @Override
  public void visit(Museum museum) {
    System.out.println("I'm visiting the Museum!");
  }

  @Override
  public void visit(Park park) {
    System.out.println("I'm visiting the Park!");
  }
}

interface Element {
  public void accept(Visitor visitor);
}

class City implements Element {

  ArrayList<Element> places = new ArrayList<Element>();

  public City() {
    places.add(new Museum());
    places.add(new Park());
  }

  @Override
  public void accept(Visitor visitor) {
    System.out.println("City is accepting visitor.");
    visitor.visit(this);

    for (Element e : places) {
      e.accept(visitor);
    }
  }
}

class Museum implements Element {
  @Override
  public void accept(Visitor visitor) {
    System.out.println("Museum is accepting visitor.");
    visitor.visit(this);
  }
}

class Park implements Element {
  @Override
  public void accept(Visitor visitor) {
    System.out.println("Park is accepting visitor.");
    visitor.visit(this);
  }

}

public class TestVisitor {
  public static void main(String[] args) {
    FirstTimeVisitor visitor = new FirstTimeVisitor();
    City city = new City();
    city.accept(visitor);
  }
}

输出:

City is accepting visitor.
I'm visiting the city!
Museum is accepting visitor.
I'm visiting the Museum!
Park is accepting visitor.
I'm visiting the Park!

JDK中的访问者模式

javax.lang.model.element.AnnotationValue明显使用了访问者模式, 但是在普通工程里并没有广泛的应用.

comments powered by Disqus