ANTLR - Няма жизнеспособна алтернатива на входа

Получавам грешката: no viable alternative at input 'mult', когато се опитвам да анализирам входа: div(mean(mult(field_a, field_b)), sum(field_b)).

Ето моята граматика:

grammar Analytics;

start: expr | stat;

expr
    : UNARY_EXPR '(' (stat | expr | NUMBER ) ')'                                        #unaryExpr
    | BINARY_EXPR '(' (stat | expr | constant) ',' (stat | expr | constant) ')'         #binaryExpr
    | MULTIPLE_EXPR '(' (stat | expr | constant) ',' (stat | expr | constant)+ ')'      #multipleExpr
    ;       

stat
    : UNARY_STAT  '(' (operation | field) ')'                                           #unaryStat
    | BINARY_STAT '(' (operation | field) ',' (operation | field) ')'                   #binaryStat
    ;

operation
    : UNARY_OPERATION '(' operation ')'                                                 #unaryOperation
    | BINARY_OPERATION '(' operation ',' operation ')'                                  #binaryOperation
    | MULTIPLE_OPERATION '(' operation ',' operation+ ')'                               #multipleOperation
    | field                                                                             #fieldOperation
    ;

constant: NUMBER;

field: IDENTIFIER;

UNARY_EXPR: 'neg' | 'const_num' | 'rev' | 'miss' | 'const_date' | 'const_str';
BINARY_EXPR: 'div' | 'pow' | 'log'; 
MULTIPLE_EXPR: 'add' | 'mult' | 'date_math' | 'concat'; 

UNARY_STAT: 'count' | 'missing' | 'min' | 'max' | 'stddev' | 'sum' | 'sumofsquares' | 'mean' | 'unique' | 'median' |
    'const_num' | 'neg' | 'abs';
BINARY_STAT: 'add' | 'mult' | 'div' | 'pow' | 'log';

UNARY_OPERATION: 'neg' | 'rev' | 'const_date' | 'const_str';
BINARY_OPERATION: 'div' | 'pow' | 'log' | 'miss'; 
MULTIPLE_OPERATION: 'add' | 'mult' | 'date_math' | 'concat'; 

OPEN_BRACKET: '(';
CLOSE_BRACKET: ')';
COMMA: ',';

NUMBER: ('0'..'9')+ ('.' ('0'..'9')+)? ;
IDENTIFIER : [a-zA-Z][a-zA-Z0-9_]*;

WS : (' ' | '\t')+ -> skip;

Какво правя грешно тук, което го кара да не съответства на mult? Има ли предложен подход, който мога да използвам за отстраняване на грешки при тази грешка?

Освен това, как мога да проверя кои алтернативи отговарят на всяко правило? Например изходът toStringTree(), който получавам, е: (start (expr div ( (stat mean ( mult ( field) , field ) ) , sum ( field ) ))). Как мога да разбера, че първото правило expr съответства на BINARY_EXPR '(' (stat | expr | constant) ',' (stat | expr | constant) ')', а не на UNARY_EXPR '(' (stat | expr | NUMBER ) ')'?


person Corey Wu    schedule 08.06.2015    source източник


Отговори (1)


Всеки път, когато един или повече символи могат да бъдат съпоставени с повече от 1 правило на лексер, правилото, дефинирано първо, ще "печели".

Тъй като входът mult може да бъде съпоставен с тези правила:

MULTIPLE_EXPR: 'add' | 'mult' | 'date_math' | 'concat'; 
BINARY_STAT: 'add' | 'mult' | 'div' | 'pow' | 'log';
MULTIPLE_OPERATION: 'add' | 'mult' | 'date_math' | 'concat'; 

първото правило, MULTIPLE_EXPR, винаги ще бъде избрано за вход mult.

Вместо това ще трябва да направите нещо подобно:

multiple_expr      : ADD | MULT | ... ; 
binary_stat        : ADD | MULT | ... ;
multiple_operation : ADD | MULT | ... ; 

ADD  : 'add';
MULT : 'mult';
...
person Bart Kiers    schedule 08.06.2015