1

我正在尝试重新创建 Tijs 的CurryOn16示例“TrafoFields”,从视频中抓取代码,但使用 Java18.rsc 语法而不是他的 Java15.rsc。我已经在 repl 中成功解析了 Example.java ,就像他在视频中所做的那样,产生了一个 var pt。然后我尝试用trafoFields(pt). 我得到的回应是:

|project://Rascal-Test/src/TrafoFields.rsc|(235,142,<12,9>,<16,11>): Syntax error: concrete syntax fragment

我的 TrafoFields.rsc 看起来像这样:

module TrafoFields

import lang::java::\syntax::Java18;

/**
 * - Make public fields private
 * - add getters and setters
 */

 start[CompilationUnit] trafoFields(start[CompilationUnit] cu) {
    return innermost visit (cu) {
        case  (ClassBody)`{
                         '  <ClassBodyDeclaration* cs1>
                         '  public <Type t> <ID f>;
                         '  <ClassBodyDeclaration* cs2>
                         '}`
         =>  (ClassBody)`{
                         '  <ClassBodyDeclaration* cs1>
                         '  private <Type t> <ID f>;
                         '  public void <ID setter>(<Type t> x) {
                         '    this.<ID f> = x;
                         '  }
                         '  public <Type t> <ID getter>() {
                         '      return this.<ID f>;
                         '  }
                         '  <ClassBodyDeclaration* cs2>
                         '}`
         when
            ID setter := [ID]"set<f>",
            ID getter := [ID]"get<f>"
    }
 }

与 Tijs 代码的唯一偏差是我已更改ClassBodyDec*ClassBodyDeclaration*,因为语法将此作为非终端。任何提示还有什么可能是错的?

更新

更多适应Java18语法的非终端重写:

  • 身份证=>身份证
4

1 回答 1

1

啊,是的,这就是具体语法可用性的致命弱点;解析错误。

请注意,通用解析器(例如 Rascal 使用的 GLL)模拟“无限前瞻”,因此可能会在实际原因之后的几个字符甚至几行报告解析错误(但从来没有!)。因此,缩短示例(增量调试)将有助于定位原因。

我在这方面的生活方式是:

  1. 首先用具体的 Java 代码片段替换所有模式漏洞。我知道 Java,所以我应该能够编写一个正确的片段来匹配这些漏洞。
  2. 如果仍然存在解析错误,现在您检查顶部非终端。是你需要的吗?还要确保在反引号内的片段开始之前和结束之后没有额外的空格。还是解析错误?首先为子非终结符写一个较短的片段。
  3. 解析错误解决了吗?这意味着其中一个模式漏洞在语法上不正确。孔的类型在这里领先,它应该是按字面意思使用语法的非终结符之一,当然在片段中的正确位置。一个接一个地添加孔,直到再次遇到错误。然后你知道原因,也可能知道解决方法。
于 2020-02-10T13:11:13.733 回答