Question

Assume this model class :

public class Car extends Vehicle implements Visitable {
  .....
  void accept(VehicleVisitor visitor){
    visitor.visit(this);
  }  
  .....
}

Use of visitor because the decision to permit certains vehicles to be awarded was made very later (after the creation of Car class).

And a specific hierarchy of Visitor with a base class named VehicleEvaluatorVisitor inheriting from CarVisitor whose goal is to inform whether vehicle merits awards or not :

public class VehicleEvaluatorVisitor implements VehicleVisitor {

  boolean mustBeAwarded;

  public visit(Car car){
    ....
    mustBeAwarded= true;   //after some conditional
  }

  .... //other visit methods

  boolean mustVehicleBeAwarded(){
    return mustBeAwarded;
  }

}

The goal of this design is to allow client to iterate through any collections of Vehicle in order to know which vehicle must to be awarded :

  ...
    VehicleEvaluatorVisitor visitor = new VehicleEvaluatorVisitor ();
    for(Vehicle vehicle : vehicules){
      vehicle.accept(visitor);
      boolean mustToBeAwarded = visitor.mustVehicleBeAwarded();
      .....
  ...

My question is : Is this an acceptable design ? (Of course, Car and award concept is just a theorical example)

Était-ce utile?

La solution

It's okay to have a state for a visitor.

But in most cases it is overcomplicated.

Consider having a visitor with a generic and you code will turn into:

Visitor interface

public interface VehicleVisitor<T> {
    ...
    T visit(Car car);
    ...
}

With car class

public class Car extends Vehicle implements Visitable {
    ...
    <T> T accept(VehicleVisitor<T> visitor){
        return visitor.visit(this);
    }
    ...
}

And visitor implementation

public class VehicleEvaluatorVisitor implements VehicleVisitor<Boolean> {

    public Boolean visit(Car car){
        ...
        return true;
        ...
    }

}

Autres conseils

The book on Design Pattern cleary state, that Visitors can accumulate state (point 5 in section "Consequences", page 336). The rest is an implementation detail ;-)

I can't see any problem with this design. It looks like a reasonable use case for the visitor pattern.

You've encapsulated the award evaluation logic inside the visitor, instead of exposing it in either the Car class or the client class. This is one of the aims of using the visitor pattern. And, of course, you'll be able to add more types of visitor later if you need to.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top