【问题标题】:Switch CommonTokenStream to ignore or enable Whitespace切换 CommonTokenStream 以忽略或启用空白
【发布时间】:2016-01-18 10:23:23
【问题描述】:

我原来的语法在解析过程中使用skip命令来忽略空格。

WS      :   [ \t]+ ->  skip ;

但是,对于重构方法,我需要根据此收据将空白令牌发送到隐藏通道以使用 TokenStreamRewriter: ANTLR4: TokenStreamRewriter output doesn't have proper format (removes whitespaces)

WS      :   [ \t]+ ->  channel(HIDDEN);

现在的问题是解析器将空格识别为我想在默认解析过程中避免的标记。

是否可以根据常规解析过程或重构方法的解析过程(使用相同的语法)在同一规则的两种不同实现之间切换?

我需要语义谓词吗?或者 CommonTokenStream 中有没有一种方法可以跳过或启用空格?

【问题讨论】:

    标签: antlr4


    【解决方案1】:

    我不确定是什么导致了您的问题。您的预期行为是正确的。

    WS [ \t]+ -> 频道(隐藏)

    会将这些标记移动到解析器未处理的通道。您不需要语义谓词,也不需要对 CommonTokenStream 进行任何特殊调用来实现这一点。

    这是我在语法中所做的,解析器看不到 WS(我的 WS 规则略有不同,但没有什么不同)。

    词法分析器(又名分词器)独立于解析器运行(并且在解析器之前),因此解析器无法做任何事情来影响词法分析器的工作方式(例如,将令牌放置在哪个通道上)。

    您可能还想查看 TokenStream 上的以下方法:

    public List<Token> getTokens(int start, int stop, int ttype)
    

    使用该方法,您可以通过提供评论标记的标记类型作为第三个参数,在开始和停止标记索引中提取评论标记列表。

    【讨论】:

    • 您好迈克,感谢您的回答。目前我跳过了空白,这使我可以检测函数、变量等以进行源分析。这工作正常。但是,当我想使用 TokenStreamRewriter (语法中有空格跳过)时,我没有得到我需要的空格,例如提取解析并替换源。因此,在我的重构过程中,我需要词法分析器中的 channel(HIDDEN) 语法来执行此操作。所以我的问题是如何在词法分析器的两种状态之间切换。否则我必须创建两个语法。
    • 我只是想补充一点,我使用 CommonTokenStream 来提取 var 和函数分配的位置。规则通道(HIDDEN)在令牌流中包含空格(我想在我的一般解析过程中避免,但在我的重构解析中不想)。
    • 您可能想要查看 ANTLR 书的第 4.5 节(标题为“重写输入流”)。使用 TokenStreamRewriter,您的解析器仍然不会“看到”隐藏的标记通道,但是您可以使用 TokenStreamRewriter 上的方法(它确实跟上隐藏通道)来修改流并将其写回。调用修饰符方法后,只需在重写时调用 getText() 即可用你的修改返回完整的输入流。它将包括来自隐藏频道的内容。
    • 但是 TokenStreamRewriter 也会看到跳过的令牌吗?因为我在我的主要语法中需要词法分析器表达式: WS : [ \t]+ -> skip ;用于常规解析。隐藏通道对我有用,但仅适用于重构解析。
    • 如果我不在主解析过程中使用 CommonTokenStream(访问我为检测变量和函数而拆分的令牌),跳过通道将起作用。类似于:间隔 sourceInterval = ctx.getSourceInterval(); int start = sourceInterval.a;令牌分配 = tokens.get(start + 2);
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-08-11
    • 1970-01-01
    • 2021-02-17
    • 2015-12-10
    相关资源
    最近更新 更多