Made the parse tree visitor walk ParseTree objects not ParserRuleContext objects. This necessitated pulling up the accept() and toStringTree(Parser) methods into ParseTree.

This commit is contained in:
Terence Parr 2012-03-01 17:57:49 -08:00
parent dd69a7532d
commit 2ba5a1f12a
4 changed files with 31 additions and 11 deletions

View File

@ -34,7 +34,6 @@ import org.antlr.v4.runtime.misc.NotNull;
import org.antlr.v4.runtime.misc.Nullable;
import org.antlr.v4.runtime.tree.ParseTree;
import org.antlr.v4.runtime.tree.ParseTreeListener;
import org.antlr.v4.runtime.tree.ParseTreeVisitor;
import java.util.ArrayList;
import java.util.Collections;
@ -132,7 +131,7 @@ public class ParserRuleContext<Symbol extends Token> extends RuleContext {
this(parent, parent!=null ? parent.s : -1 /* invoking state */, stateNumber);
}
// Double dispatch methods for listeners and visitors
// Double dispatch methods for listeners
// parse listener
public void enterRule(ParseListener<Symbol> listener) { }
@ -142,10 +141,6 @@ public class ParserRuleContext<Symbol extends Token> extends RuleContext {
public void enterRule(ParseTreeListener<Symbol> listener) { }
public void exitRule(ParseTreeListener<Symbol> listener) { }
// visitor
public <T> T accept(ParseTreeVisitor<? extends T> visitor) { return visitor.visitChildren(this); }
/** Does not set parent link; other add methods do */
public void addChild(TerminalNode<Symbol> t) {
if ( children==null ) children = new ArrayList<ParseTree>();

View File

@ -28,8 +28,11 @@
*/
package org.antlr.v4.runtime;
import org.antlr.v4.runtime.misc.*;
import org.antlr.v4.runtime.tree.*;
import org.antlr.v4.runtime.misc.Interval;
import org.antlr.v4.runtime.misc.Nullable;
import org.antlr.v4.runtime.tree.ParseTree;
import org.antlr.v4.runtime.tree.ParseTreeVisitor;
import org.antlr.v4.runtime.tree.Trees;
import org.antlr.v4.runtime.tree.gui.TreeViewer;
import javax.print.PrintException;
@ -236,6 +239,9 @@ public class RuleContext implements ParseTree.RuleNode {
return new Interval(start, stop);
}
@Override
public <T> T accept(ParseTreeVisitor<? extends T> visitor) { return visitor.visitChildren(this); }
public void inspect(Parser parser) {
TreeViewer viewer = new TreeViewer(parser, this);
viewer.open();

View File

@ -29,6 +29,7 @@
package org.antlr.v4.runtime.tree;
import org.antlr.v4.runtime.Parser;
import org.antlr.v4.runtime.RuleContext;
import org.antlr.v4.runtime.Token;
import org.antlr.v4.runtime.misc.Interval;
@ -78,6 +79,14 @@ public interface ParseTree extends SyntaxTree {
@Override
public int getChildCount() { return 0; }
@Override
public <T> T accept(ParseTreeVisitor<? extends T> visitor) { return null; }
@Override
public String toStringTree(Parser parser) {
return toString();
}
public boolean isErrorNode() { return this instanceof ErrorNodeImpl; }
@Override
@ -115,4 +124,12 @@ public interface ParseTree extends SyntaxTree {
ParseTree getParent();
@Override
ParseTree getChild(int i);
/** The ParseTreeVisitor needs a double dispatch method */
public <T> T accept(ParseTreeVisitor<? extends T> visitor);
/** Specialize toStringTree so that it can print out more information
* based upon the parser.
*/
public String toStringTree(Parser parser);
}

View File

@ -5,7 +5,7 @@ import org.antlr.v4.runtime.Token;
/** T is return type of visit methods. Use T=Void for no return type. */
public class ParseTreeVisitor<T> {
public T visit(ParserRuleContext<?> ctx) {
public T visit(ParseTree ctx) {
return ctx.accept(this);
}
@ -17,9 +17,11 @@ public class ParseTreeVisitor<T> {
* care about some nodes. The ParserRuleContext.accept() method
* walks all children by default; i.e., calls this method.
*/
public T visitChildren(ParserRuleContext<? extends Token> ctx) {
public T visitChildren(ParseTree ctx) {
T result = null;
for (ParseTree c : ctx.children) {
int n = ctx.getChildCount();
for (int i=0; i<n; i++) {
ParseTree c = ctx.getChild(i);
if ( c instanceof ParseTree.RuleNode ) {
ParseTree.RuleNode r = (ParseTree.RuleNode)c;
ParserRuleContext<?> rctx = (ParserRuleContext<? extends Token>)r.getRuleContext();