2014-04-27 4 views
0
%type <string> Id 
%type <ExprRes> Factor 
%type <ExprRes> Term 
%type <ExprRes> Expr 
%type <InstrSeq> StmtSeq 
%type <InstrSeq> Stmt 
%type <BExprRes> BExpr 
%type <ExprRes> Primary 

%token Ident   
%token IntLit 
%token Int 
%token Write 
%token IF 
%token EQ 
%token GTE 
%token LTE 
%token UM 
%token UP 

%% 

Prog   : Declarations StmtSeq        {Finish($2); } ; 
Declarations : Dec Declarations         { }; 
Declarations :              { }; 
Dec    : Int Ident {EnterName(table, yytext, &entry); }';' { }; 
StmtSeq   : Stmt StmtSeq          { $$ = AppendSeq($1, $2); } ; 
StmtSeq   :              { $$ = NULL;} ; 
Stmt   : Write Expr ';'          { $$ = doPrint($2); }; 
Stmt   : Id '=' Expr ';'          { $$ = doAssign($1, $3);} ; 
Stmt   : IF '(' BExpr ')' '{' StmtSeq '}'     { $$ = doIf($3, $6);}; 
BExpr   : Expr EQ Expr          { $$ = doBExpr($1, $3);}; 
Expr   : Expr '+' Term          { $$ = doAdd($1, $3); } ; 
Expr   : Expr '-' Term          { $$ = doMinus($1, $3); }; 
Expr   : Term            { $$ = $1; } ; 
Term   : Term '*' Factor          { $$ = doMult($1, $3); } ; 
Term   : Term '/' Factor          { $$ = doDiv($1, $3); } ; 
Term   : Factor            { $$ = $1; } ; 
Factor   : Primary            { $$ = $1;}; 
Primary   : '-'Primary            { $$ = doUnaryMinus($1);}; 

Primary   : IntLit            { $$ = doIntLit(yytext); }; 
Primary   : Ident            { $$ = doRval(yytext); }; 
Id    : Ident            { $$ = strdup(yytext);} 

이것은 내 yacc 문법입니다. 단항 마이너스를 얻으려고 노력 중입니다. x-- 예를 들면.YACC에서 후 증가/감소 연산자에 대한 문법을 ​​작성하려면 어떻게해야합니까?

그러나 나는

int num1;  
int num2; 
int num3; 
int num4; 

num3 = 100;  
num4 = 200; 
num3 = num4/num3; 
num1 = 1; 
num1 = num3-num1; 
num1--; 

print num3; 
print num4; 
print num1; 

내가 라인 num1--에서 yyerror 서브를 얻을 내 테스트 파일을 실행하려고 할 때,

yyerror는 내가 알 수있는 세부 정보가 매우 모호합니다. 나는 입력에서 오류가 발생할 때만 호출된다는 것을 알 수있다. 그 오류가 내가 문법을 쓰는 방법에 대한 나의 오해로부터 비롯된 것인지 또는 무엇이 그 오류인지를 알지 못합니다. 나는 불법 문자를 가리키는 프로그램을 가지고 있으며 그 문제는 줄의 첫 번째 '-'기호에서 오는 것이라고합니다. 내 대답을 찾거나 오류가있는 곳을 찾아 볼 생각이 있습니다.

이 내 렉스 파일입니다

%{ 
#include "yaccExample.h" 
#include "y.tab.h" 

#define YY_INPUT(buf,result,max_size) \ 
    { int c = GetSourceChar(); \ 
      result = (c == EOF) ? YY_NULL : (buf[0] = c, 1); \ 
     } 

%} 


letter [A-Za-z] 
digit [0-9] 

%% 
if        {return IF;} 
int        {return Int;} 
print       {return Write;} 
{letter}({letter}|{digit})*  {return Ident;} 
{digit}{digit}*     {return IntLit;} 
\=\=       {return EQ;} 
\-\-       {return UM;} 
\+\+       {return UP;} 
\>\=       {return GTE;} 
\<\=       {return LTE;} 
\=        {return '=';} 
\+        {return '+';} 
\*        {return '*';} 
\;        {return ';';} 
\{        {return '{';} 
\}        {return '}';} 
\(        {return '(';} 
\)        {return ')';} 

[ ]        {} 
\t        {} 
\r        {} 
\n        {} 

.    {WriteIndicator(GetCurrentColumn()); 
        WriteMessage("Illegal Character in lex");} 

%% 


yywrap() { 
} 
+0

왜 'c'태그를 질문에 포함 시켰습니까? –

+1

'x--'은 단항 마이너스가 아닙니다. '-x'는 단항 마이너스입니다. 'x--'는 사후 감소입니다. yyerror()가 파서로부터 호출 되었습니까? 아니면 렉서에서 직접 부르시겠습니까? '불법적 인 성격'이란 단어는 후자를 의미하며,이 경우 귀하는 왜 귀하가 그 이름을 부르는지 알 수 있습니다. – EJP

+0

@MahonriMoriancumer y 파일의 코드 삽입은 C 또는 C++로 작성됩니다. 왜 그가 C로 태그하지 않아야하는지 모르겠다. – EJP

답변

1

문제로 모든 소스 파일을 컴파일하는 용어에 대한 오해 . 단항 마이너스는 문법에 따라 기본 단어 앞에 단독으로 마이너스 기호를 의미합니다.

Primary   : '-'Primary 

올바른 문법 검사 코드는 다음과 같습니다. 올바르게 컴파일해야합니다.

num1 = -99; 
num1 = -num3; 
num1 = -(num3-num1); 

'-'연산자는 감소라고하며 문법에 나타나지 않습니다. 감소 연산자를 컴파일해야하는 경우 문법에 추가해야합니다.

0

은 yacc은 문법 디버깅을위한 제한적인 지원을하고있다. 이와 같은 경우 종종 도움이되는 한 가지는 YYDEBUG 전처리 기 심볼을 정의하고 yydebug을 전역이 아닌 값으로 설정하는 것입니다. 이렇게하면 덤프가 스캔되고 이동 된 모든 토큰을 표준 출력하고 파싱하는 동안 규칙이 줄어들어 도움이 될 수 있습니다.

추가 :

주요 기능에
#ifdef YYDEBUG 
    extern int yydebug; 
    yydebug = 1; 
#endif 

가 (또는 가능 yydebug을 설정하는 명령 줄 스위치를 사용), 및 -DYYDEBUG