我正在尝试使用ANTLR和C#,但由于缺少文档/教程,我发现它非常困难 . 我找到了几个旧版本的半心半意的教程,但似乎从那时起对API进行了一些重大改动 .
谁能给我一个简单的例子来说明如何创建语法并在短程序中使用它?
我终于设法将我的语法文件编译成词法分析器和解析器了,我可以在Visual Studio中编译和运行那些(在重新编译ANTLR源之后,因为C#二进制文件似乎也已经过时了! - 更不用说在没有一些修复的情况下源不会编译),但我仍然不知道如何处理我的解析器/词法分析器类 . 据说它可以在给出一些输入的情况下产生AST ......然后我应该可以做一些喜欢它的东西 .
4 回答
假设您要解析由以下标记组成的简单表达式:
-
减法(也是一元);+
另外;*
乘法;/
师;(...)
分组(子)表达式;整数和十进制数 .
ANTLR语法可能如下所示:
现在要创建一个合适的AST,在
options { ... }
部分添加output=AST;
,然后在语法中混合一些"tree operators",定义哪些标记应该是树的根 . 有两种方法可以做到这一点:在您的代币后添加
^
和!
.^
使令牌成为根,!
从令牌中排除令牌;使用"rewrite rules":
... -> ^(Root Child Child ...)
.以规则
foo
为例:并且假设您希望
TokenB
成为根,并且TokenA
和TokenC
成为其子项,并且您希望从树中排除TokenD
. 以下是使用选项1的方法:以下是使用选项2的方法:
所以,这里是树操作符的语法:
我还添加了一个
Space
规则来忽略源文件中的任何空格,并为词法分析器和解析器添加了一些额外的标记和命名空间 . 请注意,顺序很重要(首先是options { ... }
,然后是tokens { ... }
,最后是@... {}
-namespace声明) .而已 .
现在从语法文件中生成词法分析器和解析器:
并将
.cs
文件与C# runtime DLL's一起放在项目中 .您可以使用以下类测试它:
产生以下输出:
对应于以下AST:
(使用graph.gafol.net创建的图表)
请注意,ANTLR 3.3刚刚发布,CSharp目标处于“测试阶段” . 这就是我在我的例子中使用ANTLR 3.2的原因 .
如果是相当简单的语言(如上面的示例),您还可以在不创建AST的情况下动态评估结果 . 您可以通过在语法文件中嵌入纯C#代码,并让解析器规则返回特定值来实现 .
这是一个例子:
可以用 class 测试:
并产生以下输出:
编辑
你看过Irony.net吗?它's aimed at .Net and therefore works really well, has proper tooling, proper examples and just works. The only problem is that it is still a bit ' alpha-ish'所以文档和版本似乎有点改变,但如果你只是坚持一个版本,你可以做一些漂亮的事情 .
附:抱歉,你问一个关于X的问题,有人建议使用Y不同的东西; ^)
我个人的经验是,在学习C#/ .NET上的ANTLR之前,你应该有足够的时间来学习Java上的ANTLR . 这将为您提供所有构建块的知识,之后您可以在C#/ .NET上应用 .
我最近写了一些博文,
http://www.lextm.com/index.php/2012/07/how-to-use-antlr-on-net-part-i/
http://www.lextm.com/index.php/2012/07/how-to-use-antlr-on-net-part-ii/
http://www.lextm.com/index.php/2012/07/how-to-use-antlr-on-net-part-iii/
http://www.lextm.com/index.php/2012/07/how-to-use-antlr-on-net-part-iv/
http://www.lextm.com/index.php/2012/07/how-to-use-antlr-on-net-part-v/
假设您熟悉Java上的ANTLR并准备将语法文件迁移到C#/ .NET .
有一篇关于如何在这里一起使用antlr和C#的文章:
http://www.codeproject.com/KB/recipes/sota_expression_evaluator.aspx
这是NCalc创建者的一篇"how it was done"文章,它是C#的数学表达式评估者 - http://ncalc.codeplex.com
你也可以在这里下载NCalc的语法:http://ncalc.codeplex.com/SourceControl/changeset/view/914d819f2865#Grammar%2fNCalc.g
NCalc的工作原理示例:
希望它有所帮助