[antlr-interest] empty alternatives erroneously consume tokens

Michael Brade brade at informatik.uni-muenchen.de
Thu Mar 2 01:19:48 PST 2006


Hi,

I have a problem writing a grammar for parsing arithmetic expressions that 
contain mixed prefix and infix notation. For instance, this expression
  +( 1-(3+4) +(2 3)-1 )
simply means 
  1-(3+4)+2+3-1

What I would need in antlr is a syntactic predicate inside a loop, like this:

  c_expression: c_atom ( (arithmetic_op c_atom) => arithmetic_op c_atom )* ;

to test the following tokens at each repetition and quit the loop as soon as 
the predicate fails---but that doesn't work. 

So I thought about creating a recursive rule "cont" with the predicate and an 
empty alternative if the predicate fails. This is the complete little parser:

c_expression : (c_atom|c_bracket_exp|c_prefix_exp) cont ;

cont  : (arithmetic_op (c_atom|c_bracket_exp|c_prefix_exp)) 
            => arithmetic_op (c_atom|c_bracket_exp|c_prefix_exp) cont
      | { /* empty */ }
      ;

c_bracket_exp: BR_OPEN c_expression BR_CLOSE ;
c_prefix_exp : arithmetic_op BR_OPEN c_expression c_expression BR_CLOSE ;
c_atom       : INT ;

arithmetic_op: PLUS | MINUS ;

BR_OPEN: '(' ;
BR_CLOSE: ')' ;

However, instead of generating an empty "else" in cont() the generated code 
looks like this:

if ( synPredMatched221 ) {
    // here's the code for the predicate
}
else if ((_tokenSet_68.member(LA(1)))) {
    if ( inputState.guessing==0 ) {
        /* empty */
    }
}
else {
    throw new NoViableAltException(LT(1), getFilename());
}

So when parsing an expression I get 
   ....
   < c_expression; LA(1)==)
  < c_prefix_exp; LA(1)==null
  > cont; LA(1)==null
line 7:1: unexpected token: null  // here the expression ends correctly
  < cont; LA(1)==null
 < c_expression; LA(1)==null

at the end of the parse since the "else if" wants another token.
If I remove the "else if ((_tokenSet_68...." stuff and change the code to

if ( synPredMatched221 ) {
    // here's the code for the predicate
}
else {
}

it works! So what can I do to make ANTLR generate the code I want to have? 
I.e., an empty else branch?

Cheers,
-- 
Michael Brade;                 KDE Developer, Student of Computer Science
  |-mail: echo brade !#|tr -d "c oh"|s\e\d 's/e/\@/2;s/$/.org/;s/bra/k/2'
  °--web: http://www.kde.org/people/michaelb.html

KDE 4: Beyond Your Expectations
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 189 bytes
Desc: not available
Url : http://www.antlr.org/pipermail/antlr-interest/attachments/20060302/e7e70044/attachment.bin


More information about the antlr-interest mailing list