【已解决】Antlr v3代码编译出错:syntax error: antlr: NoViableAltException(37@[])

【问题】

如下的antlr v3的代码:

grammar DDParserDemo;

options {
	output = AST;
	ASTLabelType = CommonTree; // type of $stat.tree ref etc...
}

ID  :	('a'..'z'|'A'..'Z'|'_') ('a'..'z'|'A'..'Z'|'0'..'9'|'_')*
    ;

FLOAT
    :   ('0'..'9')+ '.' ('0'..'9')* EXPONENT?
    |   '.' ('0'..'9')+ EXPONENT?
    |   ('0'..'9')+ EXPONENT
    ;

COMMENT
    :   '//' ~('\n'|'\r')* '\r'? '\n' {$channel=HIDDEN;}
    |   '/*' ( options {greedy=false;} : . )* '*/' {$channel=HIDDEN;}
    ;

WS  :   ( ' '
        | '\t'
        | '\r'
        | '\n'
        ) {skip();}
    ;

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

CHAR:  '\'' ( ESC_SEQ | ~('\''|'\\') ) '\''
    ;

fragment
EXPONENT : ('e'|'E') ('+'|'-')? ('0'..'9')+ ;

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
    ;

fragment
DIGIT
	:	'0'..'9';


DECIMAL_VALUE
	:	'1'...'9' DIGIT*;

HEX_VALUE
	:	'0x' HEX_DIGIT+;
	
startParse	:	(identification)+;

identification	:	definiton WS* ','? WS*
		;
	
definiton	:	(ID)^ ('\t'!|' '!)+ (DECIMAL_VALUE | HEX_VALUE)
		;

用generate->generate code,结果出错:

syntax error antlr NoViableAltException 37

log为:

[09:25:30] error(100): DDParserDemo.g:67:7: syntax error: antlr: NoViableAltException(37@[])

[09:25:30] error(100): DDParserDemo.g:67:7: syntax error: antlr: NoViableAltException(37@[])

[09:25:30] error(100): DDParserDemo.g:0:1: syntax error: assign.types: org.antlr.runtime.EarlyExitException

[09:25:30] error(100): DDParserDemo.g:0:1: syntax error: assign.types: MismatchedTreeNodeException(3!=34)

[09:25:30] error(100): DDParserDemo.g:0:1: syntax error: assign.types: MismatchedTreeNodeException(32!=3)

[09:25:30] java.lang.ArrayIndexOutOfBoundsException: 2

    at org.antlr.tool.Rule.trackRuleReferenceInAlt(Rule.java:294)

    at org.antlr.tool.Grammar.altReferencesRule(Grammar.java:2011)

    at org.antlr.grammar.v3.DefineGrammarItemsWalker.atom(DefineGrammarItemsWalker.java:3787)

    at org.antlr.grammar.v3.DefineGrammarItemsWalker.element(DefineGrammarItemsWalker.java:2416)

    at org.antlr.grammar.v3.DefineGrammarItemsWalker.alternative(DefineGrammarItemsWalker.java:2052)

    at org.antlr.grammar.v3.DefineGrammarItemsWalker.block(DefineGrammarItemsWalker.java:1924)

    at org.antlr.grammar.v3.DefineGrammarItemsWalker.rule(DefineGrammarItemsWalker.java:1515)

    at org.antlr.grammar.v3.DefineGrammarItemsWalker.rules(DefineGrammarItemsWalker.java:1115)

    at org.antlr.grammar.v3.DefineGrammarItemsWalker.grammarSpec(DefineGrammarItemsWalker.java:578)

    at org.antlr.grammar.v3.DefineGrammarItemsWalker.grammar_(DefineGrammarItemsWalker.java:256)

    at org.antlr.tool.Grammar.defineGrammarSymbols(Grammar.java:791)

    at org.antlr.tool.CompositeGrammar.defineGrammarSymbols(CompositeGrammar.java:370)

    at org.antlr.tool.Grammar.setGrammarContent(Grammar.java:650)

    at org.antlr.works.grammar.antlr.ANTLRGrammarEngineImpl.createLexerGrammarFromCombinedGrammar(ANTLRGrammarEngineImpl.java:218)

    at org.antlr.works.grammar.antlr.ANTLRGrammarEngineImpl.createCombinedGrammar(ANTLRGrammarEngineImpl.java:204)

    at org.antlr.works.grammar.antlr.ANTLRGrammarEngineImpl.createGrammars(ANTLRGrammarEngineImpl.java:165)

    at org.antlr.works.grammar.antlr.ANTLRGrammarEngineImpl.analyze(ANTLRGrammarEngineImpl.java:272)

    at org.antlr.works.grammar.engine.GrammarEngineImpl.analyze(GrammarEngineImpl.java:325)

    at org.antlr.works.grammar.CheckGrammar.run(CheckGrammar.java:70)

    at java.lang.Thread.run(Unknown Source)

[09:25:30] error(100): D:\DevRoot\IndustrialMobileAutomation\HandheldDataSetter\ANTLR\projects\v1.5\DDParserDemo\DDParserDemo.g:67:7: syntax error: antlr: NoViableAltException(37@[])

[09:25:30] error(100): D:\DevRoot\IndustrialMobileAutomation\HandheldDataSetter\ANTLR\projects\v1.5\DDParserDemo\DDParserDemo.g:67:7: syntax error: antlr: NoViableAltException(37@[])

[09:25:30] error(100): D:\DevRoot\IndustrialMobileAutomation\HandheldDataSetter\ANTLR\projects\v1.5\DDParserDemo\DDParserDemo.g:0:1: syntax error: assign.types: org.antlr.runtime.EarlyExitException

[09:25:30] error(100): D:\DevRoot\IndustrialMobileAutomation\HandheldDataSetter\ANTLR\projects\v1.5\DDParserDemo\DDParserDemo.g:0:1: syntax error: assign.types: MismatchedTreeNodeException(3!=34)

[09:25:30] error(100): D:\DevRoot\IndustrialMobileAutomation\HandheldDataSetter\ANTLR\projects\v1.5\DDParserDemo\DDParserDemo.g:0:1: syntax error: assign.types: MismatchedTreeNodeException(32!=3)

[09:25:30] error(10):  internal error: D:\DevRoot\IndustrialMobileAutomation\HandheldDataSetter\ANTLR\projects\v1.5\DDParserDemo\DDParserDemo.g : java.lang.NullPointerException

org.antlr.tool.Grammar.generateMethodForRule(Grammar.java:1759)

org.antlr.grammar.v3.CodeGenTreeWalker.rules(CodeGenTreeWalker.java:1418)

org.antlr.grammar.v3.CodeGenTreeWalker.grammarSpec(CodeGenTreeWalker.java:1392)

org.antlr.grammar.v3.CodeGenTreeWalker.grammar_(CodeGenTreeWalker.java:503)

org.antlr.codegen.CodeGenerator.genRecognizer(CodeGenerator.java:415)

org.antlr.Tool.generateRecognizer(Tool.java:661)

org.antlr.Tool.process(Tool.java:474)

org.antlr.works.generate.CodeGenerate.generate(CodeGenerate.java:104)

org.antlr.works.generate.CodeGenerate.run(CodeGenerate.java:185)

java.lang.Thread.run(Unknown Source)

 

【解决过程】

1.后来去看了对应的66,67行,是:

DECIMAL_VALUE
	:	'1'...'9' DIGIT*;

然后和之前的代码对比后才发现,原来是,表示范围的的话,是两个点,而不是三个点:

fragment
DIGIT
	:	'0'..'9';

所以,去改为2个点:

DECIMAL_VALUE
	:	'1'..'9' DIGIT*;

即可消除出错了。

 

【总结】

antlr中的语法,虽然很多定义都和正则很类似,但是对于这个表示范围的语法,觉得还是比较诡异的。

竟然是两个点,不是三个点,需要以后写代码的时候,注意一下。



发表评论

电子邮件地址不会被公开。 必填项已用*标注

无觅相关文章插件,快速提升流量