在C#中行走ANTLR AST的教程? [英] Tutorial for walking ANTLR ASTs in C#?
问题描述
有人知道在C#中使用ANTLR生成的AST的教程吗?我能找到的最接近的是此,但不是很有帮助.
Is anyone aware of tutorials for walking ANTLR-generated ASTs in C#? The closest I was able to find is this, but it's not terribly helpful.
我的目标是浏览我正在使用的基于特定领域语言的生成树,并使用这些树输出生成的C#代码.
My goal is to walk through trees that I'm generating based on a domain-specific language that I'm working on, and to use the trees to output generated C# code.
基于Java的教程也将有所帮助-任何提供了如何遍历ANTLR AST的清晰示例的事物.
A Java-based tutorial would be helpful, too -- anything that provides clear examples of how to traverse ANTLR ASTs.
推荐答案
我通过修改这是我的版本,我刚好用它来将已解析的代码转换为C#. 这些是步骤:
Here's my version, which I happen to be using to convert parsed code to C#. These are the steps:
- 使用您的输入实例化 ANTLRStringStream 或子类(可以是文件或字符串).
- 实例化生成的词法分析器,并传入该字符串流.
- 使用词法分析器实例化令牌流.
- 使用该令牌流实例化解析器.
- 从解析器获取顶级值,并将其转换为
CommonTree
. - 遍历树:
- Instantiate an ANTLRStringStream or subclass with your input (it can be a file or string).
- Instantiate your generated lexer, passing in that string stream.
- Instantiate a token stream with the lexer.
- Instantiate your parser with that token stream.
- Get the top-level value from your parser, and turn it into a
CommonTree
. - Traverse the tree:
要获取节点的文字,请使用node.Text
.
要获取节点的令牌名称,请使用node.Token.Text
.
To get the literal text of a node, use node.Text
.
To get the token name of a node, use node.Token.Text
.
请注意,如果node.Token.Text
是虚构的令牌且没有相应的字符串,则只会为您提供令牌的实际名称.如果它是真实令牌,则node.Token.Text
将返回其字符串.
Note that node.Token.Text
will only give you the actual name of your token if it's an imaginary token with no corresponding string. If it's a real token, then node.Token.Text
will return its string.
例如,如果语法中包含以下内容:
For example, if you had the following in your grammar:
tokens { PROGRAM, FUNCDEC }
EQUALS : '==';
ASSIGN : '=';
然后您将从相应的node.Token.Text
访问中获得"PROGRAM"
,"FUNCDEC"
,"=="
和"="
.
Then you'll get "PROGRAM"
, "FUNCDEC"
, "=="
, and "="
from the corresponding accesses of node.Token.Text
.
You can see part of my example below, or you can browse the full version.
public static string Convert(string input)
{
ANTLRStringStream sStream = new ANTLRStringStream(input);
MyGrammarLexer lexer = new MyGrammarLexer(sStream);
CommonTokenStream tStream = new CommonTokenStream(lexer);
MyGrammarParser parser = new MyGrammarParser (tStream);
MyGrammarParser.program_return parserResult = parser.program();
CommonTree ast = (CommonTree)parserResult.Tree;
Print(ast);
string output = header + body + footer;
return output;
}
public static void PrintChildren(CT ast)
{
PrintChildren(ast, " ", true);
}
public static void PrintChildren(CT ast, string delim, bool final)
{
if (ast.Children == null)
{
return;
}
int num = ast.Children.Count;
for (int i = 0; i < num; ++i)
{
CT d = (CT)(ast.Children[i]);
Print(d);
if (final || i < num - 1)
{
body += delim;
}
}
}
public static void Print(CommonTree ast)
{
switch (ast.Token.Text)
{
case "PROGRAM":
//body += header;
PrintChildren(ast);
//body += footer;
break;
case "GLOBALS":
body += "\r\n\r\n// GLOBALS\r\n";
PrintChildren(ast);
break;
case "GLOBAL":
body += "public static ";
PrintChildren(ast);
body += ";\r\n";
break;
....
}
}
这篇关于在C#中行走ANTLR AST的教程?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!