Java Reference
In-Depth Information
public void visit(MachineComposite mc)
{
Iterator i = mc.getComponents().iterator();
while (i.hasNext())
{
((MachineComponent) i.next()).accept(this);
}
}
}
SOLUTION 29.4
One solution is to add a
Set
argument to all the
accept()
and
visit()
methods, so that
the set of visited nodes gets passed around. The
Process-Component
class should then
have a concrete
accept()
method that calls its abstract
accept()
method, passing it a new
Set
object:
public void accept(ProcessVisitor v)
{
accept(v, new HashSet());
}
This design is similar to the approach that Chapter 28, I
TERATOR
, used to create an iterator
for the
ProcessComponent
hierarchy.
The
ProcessAlternation
,
ProcessSequence
, and
ProcessStep
subclasses in
the
ProcessComponent
hierarchy pass the set to a visitor's
visit()
method:
public void accept(ProcessVisitor v, Set visited)
{
v.visit(this, visited);
}
Now visitor developers must create classes with
visit()
methods that accept the
visited
set. This is a significant hint that using the set is a good idea, although the visitor developer
retains the responsibility for populating the set.
SOLUTION 29.5
Alternatives to applying V
ISITOR
follow.
•
Add the behavior you need to the original hierarchy. You can achieve this if you are in
good communication with the hierarchy developers or if you are in a shop that does
not recognize code ownership.
•
You can let a class that must operate on a machine or a process structure just traverse
the structure. Note that you don't need visitor to extend, say, a
list
of items. The reason
V
ISITOR
pops up with hierarchies is that the hierarchy contains various types. But you
can detect an object's specific type with
instanceof
or by building in Booleans,
such as
isLeaf()
and
isComposite()
.
•
If the behavior you want to add is of a significantly different thrust than the existing
behavior, you can create a parallel hierarchy. For example, the
MachinePlanner