我想开始使用ANTLR,但是在antlr.org网站上花了几个小时回顾一下这些例子之后,我仍然无法清楚地理解Java进程的语法.
是否有一些简单的例子,比如使用ANTLR实现的四操作计算器,通过解析器定义并一直到Java源代码?
解析器不知道该怎么做的默认行为是将消息打印到终端,如:
第1:23行丢失DECIMAL at'}'
这是一个好消息,但在错误的地方.我宁愿接受这个作为例外.
我已经尝试过使用了BailErrorStrategy
,但这会抛出ParseCancellationException
没有消息(由a引起InputMismatchException
,也没有消息).
有没有办法让我通过异常报告错误,同时保留邮件中的有用信息?
这就是我真正想要的 - 我通常在规则中使用动作来构建对象:
dataspec returns [DataExtractor extractor]
@init {
DataExtractorBuilder builder = new DataExtractorBuilder(layout);
}
@after {
$extractor = builder.create();
}
: first=expr { builder.addAll($first.values); } (COMMA next=expr { builder.addAll($next.values); })* EOF
;
expr returns [List<ValueExtractor> values]
: a=atom { $values = Arrays.asList($a.val); }
| fields=fieldrange { $values = values($fields.fields); }
| '%' { $values = null; }
| ASTERISK { $values = values(layout); }
;
Run Code Online (Sandbox Code Playgroud)
然后当我调用解析器时,我做了类似这样的事情:
public …
Run Code Online (Sandbox Code Playgroud) 我一直在寻找很多关于这一点,我找不到任何有用的,真正帮助我建立一个AST.我已经知道ANTLR4不像以前的ANTLR3那样构建AST.每个人都说:"嘿,使用访客!",但我找不到任何示例或更详细的解释如何我这样做...
我的语法必须像C一样,但每个命令都用葡萄牙语(portuga编程语言)编写.我可以使用ANTLR4轻松生成解析树.我的问题是:现在我需要做些什么才能创建AST?
顺便说一下,我正在使用Java和IntelliJ ......
EDIT1:我能得到的最接近的是使用本主题的答案:是否有一个使用antlr4从java源代码创建AST并提取方法,变量和注释的简单示例? 但它只打印访问过的方法的名称..
由于第一次尝试对我不起作用,我试图使用ANTLR3中的这个教程,但我无法弄清楚如何使用StringTamplate而不是ST ...
阅读本书The Definitive ANTLR 4 Reference我也找不到任何与AST有关的内容.
EDIT2:现在我有一个类来创建DOT文件,我只需要弄清楚如何正确使用访问者
java compiler-construction antlr abstract-syntax-tree antlr4
我在 DataBindingMapperImpl.java 中收到一个特定数据绑定的错误,这导致在构建项目时出现以下错误。
用于代码生成的 ANTLR 工具版本 4.5.3 与当前运行时版本 4.7.1 不匹配。
用于解析器编译的 ANTLR 运行时版本 4.5.3 与当前运行时版本 4.7.1 不匹配用于代码生成的 ANTLR 工具版本 4.5.3 与当前运行时版本 4.7.1
不匹配 用于解析器编译的 ANTLR 运行时版本 4.5.3 与当前运行时版本 4.7.1
/Users/casper/Documents/ARCore/Name /app/build/generated/source/kapt/nameDebug/com/company/name/DataBinderMapperImpl.java:10: 错误:找不到符号
import com.company.name.databinding.ActivitySplashScreenBindingImpl;
^
symbol: class ActivitySplashScreenBindingImpl
> Task :app:kaptNameDebugKotlin FAILED
> Task :app:mergeExtDexNameDebug
location: package com.company.name.databinding
FAILURE: Build failed with an exception.
Run Code Online (Sandbox Code Playgroud)
然后是下面的错误消息...
我遵循了导致此问题的类似帖子here,这是上述错误消息的结尾。
FAILURE: Build failed with an exception.
* What went wrong:
Execution failed for task ':app:kaptNameDebugKotlin'.
> A failure occurred while executing …
Run Code Online (Sandbox Code Playgroud) 我最近不得不使用解析器来做项目.我下载ANTLR4
并按照本书中描述的步骤操作The Definitive ANTLR4 Reference
.以下是我在命令行中键入的步骤:
1. export CLASSPATH=".:/<Mydirectory>/antlr-4.2.2-complete.jar:$CLASSPATH"
2. alias antlr4='java -jar /<My directory>/antlr-4.2.2-complete.jar'
3. alias grun='java org.antlr.v4.runtime.misc.TestRig'
4. antlr4 Hello.g4
Run Code Online (Sandbox Code Playgroud)
所有的工作都很好,它生成我需要的java文件.但是,在我进入之后
5. grun Hello r -tokens
Run Code Online (Sandbox Code Playgroud)
它报道
无法加载Hello作为词法分析器或解析器.
我谷歌一些信息,但仍然无法弄清楚发生了什么.
我正在为学校项目创建一个简单的编程语言.我正在使用ANTLR 4从我的语法生成词法分析器和解析器.到目前为止,我一直在使用ANTLRs监听器模式来应用编程语言的实际功能.
现在我想实现if/else语句,但是我不确定在使用监听器模式时这些实际上是可以实现的,因为ANTLR决定在使用监听器时遍历解析树的顺序,我想是if /的实现else语句将要求在解析树周围跳转,具体取决于语句中的条件是否满足.
任何人都可以告诉我是否可以使用ANTLR实现if/else语句,或者我是否必须自己实现访问者模式?另外,任何人都可以给出一个非常简单的实现语句的例子吗?
我正在阅读"The Definitive Antlr 4 Reference",并了解听众和访客的工作方式.这本书特别详细地解释了监听器如何与SAX解析器相关,并且在每个解析器的实现过程中调用方法时都很明显.我还可以看到,监听器非常适合将输入转换为输出,但我很欣赏一个简短的解释/示例,关于何时使用监听器以及何时使用访问者(或者它们是否应该在某些情况下使用?).
我的特殊目的是创建一个解释器(带有一些自定义调用的Cucumber-style/TinyBasic Interpreter),它将检查语法错误并停止执行自定义函数的错误而不恢复 - 很想看到这样的事情的完整实现在antlr - 如果有人碰巧知道一个.
提前感谢任何建议.
使用Java 7语法https://github.com/antlr/grammars-v4/blob/master/java7/Java7.g4我想找到具有特定名称的方法,然后打印出该方法.我看到methodDeclaration
我匹配时可以使用规则.所以我继承Java7BaseListener
并覆盖这个监听器方法:
@Override public void enterMethodDeclaration(Java7Parser.MethodDeclarationContext ctx) { }
Run Code Online (Sandbox Code Playgroud)
如何获取原始文本? ctx.getText()
给了我一个字符串,所有的空白都被删除了.我想要评论和原始格式.
目标
我正在开发一个为Coldfusion CFscript创建Varscoper的项目.基本上,这意味着检查源代码文件以确保开发人员正确地使用var
他们的变量.
在使用ANTLR V4几天后,我有一个语法,在GUI视图中生成一个非常好的解析树.现在,使用该树,我需要一种方法来以编程方式在节点上爬行和寻找变量声明,并确保如果它们在函数内部,则它们具有适当的范围.如果可能的话,我宁愿不在语法文件中这样做,因为这需要将语言的定义与此特定任务混合.
我试过的
我最近的尝试是使用ParserRuleContext
并尝试通过它的children
通过getPayload()
.在检查了类之后,getPayLoad()
我会有一个ParserRuleContext
对象或一个Token
对象.不幸的是,使用它我永远无法找到获取特定节点的实际规则类型的方法,只有它包含文本.每个节点的规则类型都是必需的,因为该文本节点是否是被忽略的右手表达式,变量赋值或函数声明都很重要.
问题
这是我的示例java代码:
Cfscript.java
import org.antlr.v4.runtime.*;
import org.antlr.v4.runtime.tree.Trees;
public class Cfscript {
public static void main(String[] args) throws Exception {
ANTLRInputStream input = new ANTLRFileStream(args[0]);
CfscriptLexer lexer = new CfscriptLexer(input);
CommonTokenStream tokens = new CommonTokenStream(lexer);
CfscriptParser parser = new CfscriptParser(tokens);
parser.setBuildParseTree(true);
ParserRuleContext tree = parser.component();
tree.inspect(parser); // show in gui
/*
Recursively go though tree finding function declarations and …
Run Code Online (Sandbox Code Playgroud) antlr4 ×10
antlr ×6
java ×5
antlr3 ×2
android ×1
coldfusion ×1
data-binding ×1
kotlin ×1
listener ×1