0

我有以下 ANTLR 语法,它构成了更大的表达式解析器的一部分:

grammar ProblemTest;

atom    :   constant
    |   propertyname;

constant:   (INT+ | BOOL | STRING | DATETIME);

propertyname
    :   IDENTIFIER  ('/' IDENTIFIER)*;

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

INT 
    :   '0'..'9'+;

BOOL    :   ('true' | 'false');

DATETIME
    :   'datetime\'' '0'..'9'+ '-' '0'..'9'+ '-' + '0'..'9'+ 'T' '0'..'9'+ ':' '0'..'9'+ (':' '0'..'9'+ ('.' '0'..'9'+)*)* '\'';

STRING
    :  '\'' ( ESC_SEQ | ~('\\'|'\'') )* '\''
    ;

fragment
HEX_DIGIT : ('0'..'9'|'a'..'f'|'A'..'F') ;

fragment
ESC_SEQ
    :   '\\' ('b'|'t'|'n'|'f'|'r'|'\"'|'\''|'\\')
    |   UNICODE_ESC
    |   OCTAL_ESC
    ;

fragment
OCTAL_ESC
    :   '\\' ('0'..'3') ('0'..'7') ('0'..'7')
    |   '\\' ('0'..'7') ('0'..'7')
    |   '\\' ('0'..'7')
    ;

fragment
UNICODE_ESC
    :   '\\' 'u' HEX_DIGIT HEX_DIGIT HEX_DIGIT HEX_DIGIT
    ;

如果我在 ANTLR 中的解释器中调用它

'Hello\\World' 

然后这被解释为propertyname而不是constant。如果我在 C# 中编译它并在测试工具中运行它,也会发生同样的情况,所以这不是狡猾的解释器的问题

我确定我遗漏了一些非常明显的东西......但为什么会发生这种情况?很明显,字符串匹配器存在问题,但我至少会认为IDENTIFIER与 ' 字符不匹配这一事实意味着这将引发 NoViableAltException 而不是失败?

4

1 回答 1

1

首先,ANTLRWorks 和 antlr-3.5-complete.jar 都不能用于为 C# 目标生成代码。它们可能会生成以 .cs 结尾的文件,这些文件甚至可能会 compile,但这些文件与 ANTLR 工具 (Antlr3.exe) 的 C# 端口或推荐的 MSBuild 集成生成的文件不同。确保您正在通过一种经过测试的方法生成生成的解析器。

第二,INT永远不会匹配。由于IDENTIFIER出现INT在语法中,并且所有序列'0'..'9'+都匹配IDENTIFIERand INT,因此词法分析器将始终采用出现的第一个选项 ( IDENTIFIER)。

于 2013-04-16T13:16:26.383 回答