代码之家  ›  专栏  ›  技术社区  ›  Hakanai

基于当前行号有条件地跳过ANTLR lexer规则

  •  0
  • Hakanai  · 技术社区  · 4 年前

    我的ANTLR lexer语法中有这两条规则,它们匹配相同的模式,但具有互斥谓词:

    MAGIC:        '#' ~[\r\n]* {getLine() == 1}? ;
    HASH_COMMENT: '#' ~[\r\n]* {getLine() != 1}? -> skip;
    

    当我在ANTLR预览中查看令牌时,我看到:

    Screenshot of ANTLR Preview

    所以看起来谓词没有被使用,不管我在哪一行,这个标记都是神奇的。

    我还尝试了一种不同的方法来解决这个问题:

    tokens { MAGIC }
    
    HASH_COMMENT: '#' ~[\r\n]* {if (getLine() == 1) setType(MAGIC); else skip();};
    

    但现在,两人都发表了评论:

    Another screenshot of ANTLR Preview

    我真的以为第一次尝试使用两个谓词会起作用,所以这是令人惊讶的,但现在似乎这个动作也不起作用,这更奇怪。

    我该怎么做?

    我不想尝试匹配“#usda…”作为一个不同的标记,因为该注释可能出现在文件的下一行,除非位于第一行,否则应将其视为普通注释。

    0 回复  |  直到 4 年前
        1
  •  0
  •   Mike Lischke    4 年前

    我不会试图在解析步骤中强制使用语义。字母组合是一个HASH_注释,句号。

    相反,我会将其作为正常语法处理,并在解析后处理步骤中可能需要的任何特殊内容。例如:

    document: HASH_COMMENT? content EOF;
    

    通过这种方式,您可以在任何内容之前定义一个可能的HASH_注释(稍后您可能会将其解释为MAGIC,而不使用这样的标记类型)。可能不是第一行,但在其他任何行之前(这更像真实文档,在散列注释之前可以有空格)。

    推荐文章