The Boa Programming Guide - Visitors
Boa provides a custom syntax for easily performing mining tasks on source code. This syntax is inspired by the object-oriented visitor pattern. Users may declare a visitor:
Visitors are typically assigned to a variable and provide one or more visit
clauses. A visit is started using a call to the
This function takes two arguments: the starting node
n and a
This call then starts a visit at the node
n using the specified
v. By default, a depth-first search (DFS) traversal
strategy is used. The visitor defines visit clauses, which execute either
before or after visiting a node's children.
There are two different kinds of visit clauses:
Visit clauses specify an identifier and a node type. When the visitor visits
any node matching the specified node type, the clause's body executes (with the
node bound to the specified identifier). A
before visit clause
runs before the node's children are visited and an
clause runs after all of the node's children were visited.
Visit clauses may also specify a list of node types:
When specifying a list of node types, no identifier is given and the node is not accessible from the clause's body.
Each node type may appear in at most 1 before clause and at most 1 after clause.
Visitors may also contain a visit clause with a wildcard:
A wildcard visit clause will match any node type that does not already have a visit clause. This allows providing a default behavior for the visitor, with custom node-specific behavior overriding the default. Note that unlike pattern matching in functional languages, the order of the clauses does not matter as each node type will have exactly 0 or 1 matching visit clause.
Custom Traversal Strategies
By default visitors use a depth-first traversal strategy. If your analysis
requires a different strategy you may specify it. Before visit clauses allow a
special statement, called a
This statement tells the visitor to stop the depth-first traversal and return to the parent node. This is useful when you know you don't need to visit the sub-tree rooted at the current node or if you need to visit the sub-tree with a custom traversal strategy. Note that if a stop statement executes, the after clause (if any) for that node will not execute.
You may also specify to visit a specific child node, by using the single-argument form of the visit function:
This states to visit the
child node, using the current visitor. A
combination of stop statements and visit calls can be used to implement a
custom traversal strategy.