clean up tree output, rename _ctx to context

[git-p4: depot-paths = "//depot/code/antlr4/main/": change = 9058]
This commit is contained in:
parrt 2011-09-08 12:12:51 -08:00
parent b671cb1fba
commit da7e7c8813
8 changed files with 71 additions and 70 deletions

View File

@ -28,11 +28,15 @@
*/
package org.antlr.v4.runtime;
import org.antlr.v4.runtime.atn.*;
import org.antlr.v4.runtime.atn.ATN;
import org.antlr.v4.runtime.atn.ATNState;
import org.antlr.v4.runtime.misc.Interval;
import org.antlr.v4.runtime.tree.*;
import org.antlr.v4.runtime.tree.ParseTree;
import org.antlr.v4.runtime.tree.ParseTreeListener;
import org.antlr.v4.runtime.tree.Trees;
import java.util.*;
import java.util.ArrayList;
import java.util.List;
/** Rules can return start/stop info as well as possible trees and templates.
* Each context knows about invoking context and pointer into ATN so we
@ -277,12 +281,18 @@ public class RuleContext implements ParseTree.RuleNode {
return new Interval(start, stop);
}
public String toStringTree() {
return Trees.toStringTree(this);
/** Print out a whole tree, not just a node, in LISP format
* (root child1 .. childN). Print just a node if this is a leaf.
* We have to know the recognizer so we can get rule names.
*/
public String toStringTree(BaseRecognizer recog) {
return Trees.toStringTree(this, recog);
}
public void discover(ParseTreeListener listener) { }
public void finish(ParseTreeListener listener) { }
public String toStringTree() { return toStringTree(null); }
public void enterRule(ParseTreeListener listener) { }
public void exitRule(ParseTreeListener listener) { }
public String toString() {
return toString(null);

View File

@ -38,12 +38,12 @@ public class ParseTreeVisitor {
return;
}
ParseTree.RuleNode r = (ParseTree.RuleNode)t;
discoverRule(listener, r);
enterRule(listener, r);
int n = r.getChildCount();
for (int i = 0; i<n; i++) {
visit(listener, r.getChild(i));
}
finishRule(listener, r);
exitRule(listener, r);
}
protected void visitToken(ParseTreeListener listener, ParseTree.TokenNode t) {
@ -55,15 +55,15 @@ public class ParseTreeVisitor {
* First we trigger the generic and then the rule specific.
* We to them in reverse order upon finishing the node.
*/
protected void discoverRule(ParseTreeListener listener, ParseTree.RuleNode r) {
protected void enterRule(ParseTreeListener listener, ParseTree.RuleNode r) {
ParserRuleContext ctx = (ParserRuleContext)r.getRuleContext();
listener.discoverRule((ParserRuleContext)r.getRuleContext());
ctx.discover(listener);
ctx.enterRule(listener);
}
protected void finishRule(ParseTreeListener listener, ParseTree.RuleNode r) {
protected void exitRule(ParseTreeListener listener, ParseTree.RuleNode r) {
ParserRuleContext ctx = (ParserRuleContext)r.getRuleContext();
ctx.finish(listener);
ctx.exitRule(listener);
listener.finishRule(ctx);
}
@ -108,4 +108,4 @@ class s_ctx extends ParserRuleContext {
public void discover(TListener listener) { listener.discover_s(this); }
public void finish(TListener listener) { listener.discover_s(this); }
}
*/
*/

View File

@ -29,27 +29,49 @@
package org.antlr.v4.runtime.tree;
import java.util.*;
import org.antlr.v4.runtime.BaseRecognizer;
import org.antlr.v4.runtime.Token;
import java.util.ArrayList;
import java.util.List;
import java.util.Set;
import java.util.TreeSet;
/** A set of utility routines useful for all kinds of ANTLR trees */
public class Trees {
/** Print out a whole tree in LISP form. toString is used on the
* node payloads to get the text for the nodes.
* node payloads to get the text for the nodes. Detect
* parse trees and extract data appropriately.
*/
public static String toStringTree(Tree t) {
if ( t.getChildCount()==0 ) return t.getPayload().toString();
public static String toStringTree(Tree t, BaseRecognizer recog) {
if ( t.getChildCount()==0 ) return getNodeText(t, recog);
StringBuilder buf = new StringBuilder();
buf.append("(");
buf.append(t.getPayload().toString());
buf.append(getNodeText(t, recog));
buf.append(' ');
for (int i = 0; i<t.getChildCount(); i++) {
if ( i>0 ) buf.append(' ');
buf.append(t.getChild(i).toStringTree());
buf.append(toStringTree(t.getChild(i), recog));
}
buf.append(")");
return buf.toString();
}
public static String getNodeText(Tree t, BaseRecognizer recog) {
if ( recog!=null ) {
if ( t instanceof ParseTree.RuleNode ) {
int ruleIndex = ((ParseTree.RuleNode)t).getRuleContext().ruleIndex;
String ruleName = recog.getRuleNames()[ruleIndex];
return ruleName;
}
else if ( t instanceof ParseTree.TokenNode ) {
Token tok = ((ParseTree.TokenNode) t).getToken();
return tok.getText();
}
}
return t.getPayload().toString();
}
/** Walk upwards and get first ancestor with this token type. */
public static AST getAncestor(AST t, int ttype) {
t = t.getParent();

View File

@ -1,4 +1,5 @@
import org.antlr.v4.runtime.*;
import org.antlr.v4.runtime.ANTLRFileStream;
import org.antlr.v4.runtime.CommonTokenStream;
public class TestT {
public static void main(String[] args) throws Exception {
@ -10,7 +11,7 @@ public class TestT {
// }
TParser p = new TParser(tokens);
p.setBuildParseTrees(true);
ParserRuleContext ret = p.s();
// System.out.println(((Tree)ret.tree).toStringTree());
TParser.sContext ret = p.s();
System.out.println(ret.toStringTree(p));
}
}

View File

@ -1,40 +0,0 @@
/*
[The "BSD license"]
Copyright (c) 2011 Terence Parr
All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions
are met:
1. Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
2. Redistributions in binary form must reproduce the above copyright
notice, this list of conditions and the following disclaimer in the
documentation and/or other materials provided with the distribution.
3. The name of the author may not be used to endorse or promote products
derived from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
import org.antlr.v4.runtime.*;
public class TestU {
public static void main(String[] args) throws Exception {
ULexer t = new ULexer(new ANTLRFileStream(args[0]));
CommonTokenStream tokens = new CommonTokenStream(t);
UParser p = new UParser(tokens);
ParserRuleContext ret = p.s();
// System.out.println(((Tree)ret.tree).toStringTree());
}
}

View File

@ -39,8 +39,8 @@ ListenerFile(listener) ::= <<
@SuppressWarnings({"all", "warnings", "unchecked", "unused"})
public interface <listener.grammarName>Listener {
<listener.rules:{r |
void enterRule(<listener.parserName>.<r.name>_ctx ctx);
void exitRule(<listener.parserName>.<r.name>_ctx ctx);}; separator="\n">
void enterRule(<listener.parserName>.<r.name>Context ctx);
void exitRule(<listener.parserName>.<r.name>Context ctx);}; separator="\n">
}
>>
@ -408,6 +408,11 @@ RuleContextListDecl(rdecl) ::= "List\<<rdecl.ctxName>> <rdecl.name> = new ArrayL
/** Default RuleContext type name for a Parser rule */
ParserRuleContext() ::= "ParserRuleContext"
/** The rule context name is the rule followed by a suffix; e.g.,
* r becomes rContext.
*/
RuleContextNameSuffix() ::= "Context"
ImplicitTokenLabel(tokenName) ::= "_t<tokenName>"
ImplicitRuleLabel(ruleName) ::= "_r<ruleName>"
ImplicitSetLabel(id) ::= "_tset<id>"
@ -424,8 +429,8 @@ public static class <s.name> extends ParserRuleContext {
super(parent, state);
<s.ctorAttrs:{a | this.<a.name> = <a.name>;}; separator="\n">
}
public void enterRule(<parser.name>Listener listener) { listener.enterRule(this); }
public void exitRule(<parser.name>Listener listener) { listener.exitRule(this); }
public void enterRule(<parser.grammarName>Listener listener) { listener.enterRule(this); }
public void exitRule(<parser.grammarName>Listener listener) { listener.exitRule(this); }
}
>>

View File

@ -208,7 +208,7 @@ public class Target {
if ( r.g.isLexer() ) {
return gen.templates.getInstanceOf("ParserRuleContext").render();
}
return r.name+"_ctx";
return r.name+gen.templates.getInstanceOf("RuleContextNameSuffix").render();
// boolean hasNoExternallyVisibleElements =
// r.args==null && r.retvals==null && r.scope==null && r.getLabelNames()==null;
// if ( hasNoExternallyVisibleElements ) {
@ -227,7 +227,7 @@ public class Target {
if ( r.g.isLexer() ) {
return gen.templates.getInstanceOf("ParserRuleContext").render();
}
return r.name+"_ctx";
return r.name+gen.templates.getInstanceOf("RuleContextNameSuffix").render();
// boolean hasNoExternallyVisibleElements =
// r.args==null && r.retvals==null && r.scope==null && r.getLabelNames()==null;
//

View File

@ -30,13 +30,15 @@
package org.antlr.v4.codegen.model;
import org.antlr.v4.codegen.OutputModelFactory;
import org.antlr.v4.tool.*;
import org.antlr.v4.tool.Grammar;
import org.antlr.v4.tool.Rule;
import java.util.*;
/** */
public class Parser extends OutputModelObject {
public String name;
public String grammarName;
public Map<String,Integer> tokens;
public String[] tokenNames;
public Set<String> ruleNames;
@ -52,6 +54,7 @@ public class Parser extends OutputModelObject {
this.factory = factory;
this.file = file; // who contains us?
Grammar g = factory.getGrammar();
grammarName = g.name;
name = g.getRecognizerName();
tokens = new LinkedHashMap<String,Integer>();
for (String t : g.tokenNameToTypeMap.keySet()) {