我目前正在尝试在Antlr4 Visitor的帮助下开发JavaScript编译器。我已经用Java实现了这个,但无法弄清楚如何在JavaScript中做到这一点。也许有人可以回答我几个问题?
1:在Java中有一个Visitor.visit函数。如果我是对的,这在Javascript中是不可能的。有解决方法吗?
2:我的Javascript访问者获得了所有生成的访问函数,但是当我使用console.log(ctx(时,上下文是未定义的。知道为什么吗?
摘自SimpleVisitor.js:
// Visit a parse tree produced by SimpleParser#parse.
SimpleVisitor.prototype.visitParse = function(ctx) {
console.log(ctx);
};
主 js 文件:
var antlr4 = require('lib/antlr4/index');
var SimpleLexer = require('antlr4/SimpleLexer');
var SimpleParser = require('antlr4/SimpleParser');
var SimpleVisitor = require('antlr4/SimpleVisitor');
var input = "double hallo = 1;";
var chars = new antlr4.InputStream(input);
var lexer = new SimpleLexer.SimpleLexer(chars);
var tokens = new antlr4.CommonTokenStream(lexer);
var parser = new SimpleParser.SimpleParser(tokens);
var visitor = new SimpleVisitor.SimpleVisitor();
parser.buildParseTrees = true;
var tree = parser.parse();
visitor.visitParse();
这可能足以开始...
布鲁诺
编辑:
可能上下文是未定义的,因为我调用没有参数的函数,但我从哪里获得"开始"上下文?
编辑2:
所以我想我明白这应该如何解决。剩下的一个问题如何确定接下来在每个访问者函数中调用哪个规则?
访问者背后的基本思想是你必须自己处理所有的逻辑。为此,我使用 antlr 生成了访问者。我自己的访问者会覆盖实现逻辑所需的所有函数。
-
创建词法分析器、令牌...
var antlr4 = require('antlr4/index'); var SimpleJavaLexer = require('generated/GrammarLexer'); var SimpleJavaParser = require('generated/GrammarParser'); var SimpleJavaVisitor = require('generated/GrammarVisitor'); var Visitor = require('./Visitor'); var input = "TestInput"; var chars = new antlr4.InputStream(input); var lexer = new GrammarLexer.GrammarLexer(chars); var tokens = new antlr4.CommonTokenStream(lexer); var parser = new GrammarParser.GrammarParser(tokens); var visitor = new Visitor.Visitor(); parser.buildParseTrees = true; var tree = parser.parse();
-
并调用您的入口函数
visitor.visitTest(tree);
-
在新访问者内部,您需要实现新逻辑以确定下一步要调用哪个函数(正确的上下文作为参数很重要(
var GrammarVisitor = require('generated/GrammarVisitor').GrammarVisitor; function Visitor () { SimpleJavaVisitor.call(this); return this; }; Visitor.prototype = Object.create(GrammarVisitor.prototype); Visitor.prototype.constructor = Visitor; Visitor.prototype.visitTest = function(ctx) { // implement logic to determine which function to visit // then call next function and with the right context this.visitBlock(ctx.block()); };
我希望你能理解我的基本想法。如果有人有任何问题,请发表评论。