Jison 递归

Jison recursion

我正在尝试了解 Jison。不过我有点麻烦。下面的解析器总是returns[],不管你给它什么

%lex
%%

"data"\s*             return 'DATA'
[A-Za-z][A-Za-z0-9_]* return 'IDENTIFIER'
[0-9]+("."[0-9]+)?\b  return 'NUMBER'
"="                   return 'ASSIGN'
("<-"|"<+-")          return 'REACT'
"+"                   return '+'
"-"                   return '-'
"*"                   return '*'
"/"                   return '/'
"^"                   return '^'
\n+                   return 'NL'
<<EOF>>               return 'EOF'
.                     return 'INVALID'

/lex

%token NL

/* operator associations and precedence */

%left ASSIGN
%left REACT
%left '+' '-'
%left '*' '/'
%left '^'
%left UMINUS

%start program

%% /* language grammar */

program
    :
        {return [];}
    | program statement
        {return .concat([]);}
    | program statement EOF
        {return .concat([]);}
    ;

statement
    : assign NL
        {return ;}
    ;

assign
    : IDENTIFIER ASSIGN expression
        {return ['assign', , ];}
    | IDENTIFIER REACT expression
        {return ['react', , , ];}
    ;

expression
    : NUMBER
        {return +;}
    | IDENTIFIER
    ;

问题显然出在我对非终结符的定义上program。声明它的正确方法是什么?

正如 Aadit M. Shah 在评论中指出的那样,问题是在解析完成之前,您不能 return 在 jison 语法操作中。如果解析器规则执行 return,解析器本身将 return。您需要将语义值分配给 $$.

尝试:

%start program

%% /* language grammar */

program
    : EOF
        { return []; }
    | statements EOF
        { return ; }
    ;
statements
    : statement
        { $$ = []; }
    | statements statement
        { .push(); $$ = ; }
    ;

此外,将 returns 替换为 "$$ = "

statement
    : assign NL
        { $$ = ; }
    ;

assign
    : IDENTIFIER ASSIGN expression
        { $$ = ['assign', , ]; }
    | IDENTIFIER REACT expression
        { $$ = ['react', , , ]; }
    ;

expression
    : NUMBER
        { $$ = ; }
    | IDENTIFIER
        {/*add something here like $$ =  to keep the original value*/}
    ;