ANTLR4性能的起点

时间:2018-06-23 12:59:05

标签: antlr4

我已经将相当大的ANTLR2 grammar迁移到ANTLR4,并达到了一个步骤,除了少数情况外,两个语法的输出几乎相同。但是,有些文件解析太长(即使使用SLL预测模式和BailOutStrategy),所以我想知道如何找到应该首先修复的规则。

我已经使用Parser#setProfile()收集了一些统计信息,但是我不知道如何解释每个DecisionInfo对象中的结果。是否有关于如何开始优化大型ANTLR4语法并找到首先追逐哪只兔子的良好文档?

1 个答案:

答案 0 :(得分:0)

由于我不知道在DecisionInfo对象中查找什么,因此找到了以下内容,并帮助我将解析时间至少缩短了一个数量级。

首先,我使用org.antlr.v4.runtime.Parser.setProfile(boolean profile)对语法进行概要分析,然后对数以千计的文件使用org.antlr.v4.runtime.Parser.getInterpreter().setPredictionMode(PredictionMode.SLL)执行解析器,并浏览具有最高预测时间的规则:

Arrays.stream(parser.getParseInfo().getDecisionInfo())
          .filter(decision -> decision.timeInPrediction > 100000000)
          .sorted((d1, d2) -> Long.compare(d2.timeInPrediction, d1.timeInPrediction))
          .forEach(decision -> System.out.println(
                String.format("Time: %d in %d calls - LL_Lookaheads: %d Max k: %d Ambiguities: %d Errors: %d Rule: %s",
                    decision.timeInPrediction / 1000000,
                    decision.invocations, decision.SLL_TotalLook,
                    decision.SLL_MaxLook, decision.ambiguities.size(), 
                    decision.errors.size(), Proparse.ruleNames[Proparse._ATN.getDecisionState(decision.decision).ruleIndex])))

,然后使用相同的兰巴以最大的最大前瞻方式进行操作,除了:

filter(decision -> decision.SLL_MaxLook > 50).sorted((d1, d2) -> Long.compare(d2.SLL_MaxLook, d1.SLL_MaxLook))

这给了我4条规则,这些规则大部分时间都花在了哪里,在这种情况下,这足以了解必须更改的内容(通过知道在哪里寻找问题)。