为什么有多种选择?

时间:2013-02-01 14:45:07

标签: antlr

我有一个简单的语法试图解析两种类型的文本,该行以“#include”开头,其他。这是我的语法:

cmds
    : cmd+
    ;

cmd
    : include_cmd |  other_cmd
    ;

include_cmd
    : INCLUDE  DOUBLE_QUOTE  FILE_NAME  DOUBLE_QUOTE
    ;

other_cmd
    : (~'#')+
    ;


INCLUDE
    : '#include'
    ;

DOUBLE_QUOTE
    : '"'
    ;

FILE_NAME
    : ('a'..'z' | 'A'..'Z' | '0'..'9' | '_')+
    ;

New_Line 
    : ('\r' | '\n')+   
    ;

WS 
    : ('\t' | ' ')+  {$channel = HIDDEN;}
    ;

但我得到了这样的警告:

Decision can match input such as "INCLUDE DOUBLE_QUOTE FILE_NAME DOUBLE_QUOTE" using multiple alternatives: 1, 2

As a result, alternative(s) 2 were disabled for that input

我不确定如何解释此警告。其中的示例“INCLUDE DOUBLE_QUOTE FILE_NAME DOUBLE_QUOTE”应仅匹配include_cmd,因为“other_cmd”不以“#”开头。

你能帮助这里发生什么吗?

我正在使用antlr3.4。

更新 - 感谢greydet建议,在将other_cmd规则更改为(~INCLUDE)+之后,该警告消失了。但实际上还有另一个警告,

Decision can match input such as "{DOUBLE_QUOTE..FILE_NAME, New_Line..WS}" using multiple alternatives: 1, 2

As a result, alternative(s) 2 were disabled for that input

现在我想这是因为双引号可以匹配other_cmd规则和DOUBLE_QUOTE规则,但我想知道这里,一个是解析器规则,另一个是词法分析器规则,这个警告是否有意义?我根本不能使用DOUBLE_QUOTE,而是直接使用“在解析器规则include_cmd中,但这不容易阅读。

有任何帮助可以清除此警告吗?

一个附带问题 - 警告信息只是说替代1,2,但我不清楚什么是1,什么是2,有没有办法让antlr提供更直接的选择?

1 个答案:

答案 0 :(得分:1)

other_cmd规则将匹配不以#令牌开头的每个令牌序列 include_cmd规则将匹配以#include令牌开头的序列。

由于##include是两个不同的令牌,因此以#include令牌开头的令牌序列会匹配这两个规则。

尝试使用以下规则:

other_cmd
    : (~INCLUDE)+
    ;