可以直接在Antlr4网站进行实践:ANTLR Lab: learn, test, and experiment with ANTLR grammars online!
这里有很多语言的例子:grammars-v4/lisp at master · antlr/grammars-v4
中文文档:ANTLR v4 中文文档
学习 ANTLR4 是一个非常棒的选择!它是一个功能强大且灵活的语法分析器生成器,适用于构建各种语言工具。以下是一些建议,帮助你更有效地学习 ANTLR4:
ANTLR4学习资料
1. 学习基础知识
- 编译原理: 了解编译器的基本概念,如词法分析、语法分析、语义分析等。可以阅读一些经典的编译原理书籍,如《编译原理》(龙书)或《现代编译原理》(虎书)。
- 形式语言与自动机: 了解形式语言、正则文法、上下文无关文法、有限状态自动机、下推自动机等概念,这对理解 ANTLR4 的工作原理非常有帮助。
2. 安装 ANTLR4 工具
- 安装 ANTLR4 运行时库: 根据你使用的编程语言,安装相应的 ANTLR4 运行时库。例如,如果你使用 Java,可以使用 Maven 或 Gradle 添加 ANTLR4 的依赖。
- 下载 ANTLR4 工具: 下载 ANTLR4 的命令行工具,包括
antlr4
(用于生成词法分析器和语法分析器代码) 和grun
(用于测试语法规则)。
3. 学习 ANTLR4 语法
- ANTLR4 语法文件: 学习如何编写 ANTLR4 语法文件(
.g4
文件),包括定义词法规则 (lexer rules) 和语法规则 (parser rules)。 - 词法规则: 学习如何使用正则表达式定义词法规则,例如标识符、数字、字符串等。
- 语法规则: 学习如何使用上下文无关文法定义语法规则,例如表达式、语句、函数定义等。
- 语法分析树: 了解 ANTLR4 如何生成语法分析树 (parse tree),以及如何使用
Visitor
或Listener
模式遍历语法分析树。
4. 实践项目
- 简单计算器: 从一个简单的计算器开始,逐步增加功能,例如支持变量、函数调用等。
- JSON 解析器: 尝试编写一个 JSON 解析器,将 JSON 字符串解析为数据结构。
- 领域特定语言 (DSL): 设计并实现一个简单的 DSL,用于特定领域的任务,例如配置管理、数据处理等。
- 代码生成器: 尝试编写一个代码生成器,将一种语言的代码转换为另一种语言的代码。
5. 阅读 ANTLR4 官方文档
- ANTLR4 官方文档非常详细,包含了 ANTLR4 的各种特性和使用方法。
6. 阅读书籍
- 《The Definitive ANTLR 4 Reference》: Terence Parr 编写的 ANTLR4 权威参考书,强烈推荐阅读。
7. 参与社区
- ANTLR 社区: 加入 ANTLR 社区,参与讨论、提问、分享经验,与其他 ANTLR4 开发者交流。
- GitHub: 在 GitHub 上搜索 ANTLR4 相关的项目,学习其他开发者的代码。
8. 示例代码
以下是一个简单的 ANTLR4 语法文件示例(Calc.g4):
grammar Calc;
// Parser Rules
prog: stat+ ;
stat: expr NEWLINE # printExpr
| ID '=' expr NEWLINE # assign
| NEWLINE # blank
;
expr: expr op=('*'|'/') expr # MulDiv
| expr op=('+'|'-') expr # AddSub
| INT # int
| ID # id
| '(' expr ')' # parens
;
// Lexer Rules
ID : [a-zA-Z]+ ;
INT : [0-9]+ ;
NEWLINE : '\r'? '\n' ;
WS : [ \t]+ -> skip ;
9. 学习资源
- ANTLR 官方网站: ANTLR
- 《The Definitive ANTLR 4 Reference》: Terence Parr 著。
希望这些建议能帮助你更好地学习 ANTLR4!
VSCode插件安装
ANTLR4 有插件,在VSCode插件系统里搜索ANTLR4 grammar syntax support 即可。
python ANTlR4使用
官网:ANTLR
学习参考:raw.githubusercontent.com/antlr/antlr4/master/doc/getting-started.md
pip安装
pip install antlr4-tools
语法测试文件
一个小例子Expr.g4 ,将下面代码存到文件里。
grammar Expr;
prog: expr EOF ;
expr: expr ('*'|'/') expr
| expr ('+'|'-') expr
| INT
| '(' expr ')'
;
NEWLINE : [\r\n]+ -> skip;
INT : [0-9]+ ;
分析测试
执行语法分析
E:\work\antlr4>antlr4-parse Expr.g4 prog -tree
10+20+3
^Z
(prog:1 (expr:2 (expr:2 (expr:3 10) + (expr:3 20)) + (expr:3 3)) <EOF>)
先键入命令:antlr4-parse Expr.g4 prog -tree
然后键入10+20+3 回车
最后键入^z 退出(注意,windows下键入^z,且还需要一个回车。linux下键入^D 退出)
退出的时候会看到语法分析输出:(prog:1 (expr:2 (expr:2 (expr:3 10) + (expr:3 20)) + (expr:3 3)) <EOF>)
详细语法分析
E:\work\antlr4>antlr4-parse Expr.g4 prog -tokens -trace
10+20*30
^Z
[@0,0:1='10',<INT>,1:0]
[@1,2:2='+',<'+'>,1:2]
[@2,3:4='20',<INT>,1:3]
[@3,5:5='*',<'*'>,1:5]
[@4,6:7='30',<INT>,1:6]
[@5,10:9='<EOF>',<EOF>,2:0]
enter prog, LT(1)=10
enter expr, LT(1)=10
consume [@0,0:1='10',<8>,1:0] rule expr
enter expr, LT(1)=+
consume [@1,2:2='+',<3>,1:2] rule expr
enter expr, LT(1)=20
consume [@2,3:4='20',<8>,1:3] rule expr
enter expr, LT(1)=*
consume [@3,5:5='*',<1>,1:5] rule expr
enter expr, LT(1)=30
consume [@4,6:7='30',<8>,1:6] rule expr
exit expr, LT(1)=<EOF>
exit expr, LT(1)=<EOF>
exit expr, LT(1)=<EOF>
consume [@5,10:9='<EOF>',<-1>,2:0] rule prog
exit prog, LT(1)=<EOF>
看语法树gui
antlr4-parse Expr.g4 prog -gui
10+20*30
^Z
输入方法为,先输入 antlr4-parse Expr.g4 prog -gui ,然后键入10+20*30
然后键入Ctrl+z ,回车后,就会看到语法树的gui页面了:
生成解析器代码
执行
antlr4 Expr.g4
这样默认应该是生成java的解析器代码。如果要生成python3代码,执行:
antlr4 -Dlanguage=Python3 Expr.g4
测试解析器
写测试脚本,将下面代码写入test.py文件
import ExprLexer
import ExprParser
import antlr4
input = "10+20*30"
input_stream = antlr4.InputStream(input)
lexer = ExprLexer.ExprLexer(input_stream)
tokens = antlr4.CommonTokenStream(lexer)
parser = ExprParser.ExprParser(tokens)
tree = parser.prog()
print(tree.toStringTree(recog=parser))
运行测试
python test.py
输出:
(prog (expr (expr 10) + (expr (expr 20) * (expr 30))) )
测试成功。
换一个例子
先生成Hello.g4文件:
// Define a grammar called Hello
grammar Hello;
r : 'hello' ID ; // match keyword hello followed by an identifier
ID : [a-z]+ ; // match lower-case identifiers
WS : [ \t\r\n]+ -> skip ; // skip spaces, tabs, newlines
然后
$ antlr4 Hello.g4
$ javac Hello*.java
执行测试
grun Hello r -tree
## A First Example In a temporary directory, put the following grammar inside file Hello.g4: Hello.g4 ``` // Define a grammar called Hello grammar Hello; r : 'hello' ID ; // match keyword hello followed by an identifier ID : [a-z]+ ; // match lower-case identifiers WS : [ \t\r\n]+ -> skip ; // skip spaces, tabs, newlines ``` Then run ANTLR the tool on it: ``` $ cd /tmp $ antlr4 Hello.g4 $ javac Hello*.java ``` Now test it: ``` $ grun Hello r -tree (Now enter something like the string below) hello parrt (now,do:) ^D (The output:) (r hello parrt) (That ^D means EOF on unix; it's ^Z in Windows.) The -tree option prints the parse tree in LISP notation. It's nicer to look at parse trees visually. $ grun Hello r -gui hello parrt ^D ``` That pops up a dialog box showing that rule `r` matched keyword `hello` followed by identifier `parrt`.
版本3下载安装等(不需要)
点击下载这个:http://www.antlr3.org/download/antlrworks-1.5.1.jar
这个下载:http://www.antlr3.org/download/antlr-3.5.3-complete-no-st3.jar
使用命令:
java -jar /path/to/antlr4-4.13.2-complete.jar Expr.g4 -Dlanguage=Python3
总结
ANTLR(ANother Tool for Language Recognition)是一款功能强大且灵活的工具,能够处理复杂的语法规则,支持多种语言特性的定义,ANTLR支持生成多种编程语言的解析器代码,如Java、C#、Python等,这大大方便了不同语言环境下的开发者使用,提高了工具的通用性和可移植性。
个人感觉简单应用的话,Windows下安装不需要像官网讲的那样麻烦。python版本只需要pip安装即可,pip安装的时候会自动安装java,但考虑国内情况,还是建议手工安装java。
调试
报错python test.py ModuleNotFoundError: No module named 'ExprLexer'
python test.py
Traceback (most recent call last):
File "E:\work\antlr4\test.py", line 1, in <module>
import ExprLexer
ModuleNotFoundError: No module named 'ExprLexer'
没有ExprLexer这个库啊,而且库名还有大写?
先闷头安装:
pip install starlette
这不对劲啊,装错了
原来要这样装:
pip install antlr4-tools
不行,又试
pip install antlr4-python3-runtime
还是不行。
暂时未解决。
后来才知道是要用这条命令生成
antlr4 -Dlanguage=Python3 Expr.g4
执行antlr4 显示:Downloading antlr4-4.13.2-complete.jar
速度很慢,手工npm install antlr4-tool 也不行。
阿里云maven镜像
-
https://maven.aliyun.com/nexus/content/groups/public/
也可以在这里搜索:仓库服务
搜索文件:antlr4-4.13.2-complete.jar ,但是并没有找到。
好长时间后显示:ANTLR tool needs Java to run; install Java JRE 11 yes/no (default yes)?
选择yes ,然后继续
碰到报错:jdk.JdkError: [Errno 13] Permission denied: 'C:\\Users\\Admin\\.jre\\jdk-11.0.26+4-jre\\bin\\ucrtbase.dll'
用管理员账户进入cmd,报错:Error: could not open `C:\Users\Admin\.jre\jdk-11.0.26+4-jre\lib\jvm.cfg'
没搞定,先放弃。
后手工安装java11解决。
install Java JRE 11 报错,尝试手工安装
从这里下载:Java Downloads | Oracle
但是官网需要注册才能下载。也可以从这里下载:
下载完毕后安装。安装完毕再来试试命令:
antlr4 -Dlanguage=Python3 Expr.g4
没有报错!解决了前面执行antlr4报错的问题。
执行python test.py 报错:line 1:8 missing NEWLINE at '<EOF>'
因为是在windows下,需要加回车
input = "10+20*30\r\n"
后来发现,是自己的Expr.g4文件有问题,应该是:
grammar Expr;
prog: expr EOF ;
expr: expr ('*'|'/') expr
| expr ('+'|'-') expr
| INT
| '(' expr ')'
;
NEWLINE : [\r\n]+ -> skip;
INT : [0-9]+ ;
原来写的是:
grammar Expr;
prog: (expr NEWLINE)* ;
expr: expr ('*'|'/') expr
| expr ('+'|'-') expr
| INT
| '(' expr ')'
;
NEWLINE : [\r\n]+ ;
INT : [0-9]+ ;
用新的即可。
报错:HelloParser.java:74: 错误: 方法不会覆盖或实现超类型的方法
@Override
这行这段代码的时候报错:
$ antlr4 Hello.g4
$ javac Hello*.java
估计可能是因为windows10的原因。
学习参考书
https://github.com/Philippe-Laval/tpantlr2