中间代码生成程序三地址.docx
《中间代码生成程序三地址.docx》由会员分享,可在线阅读,更多相关《中间代码生成程序三地址.docx(8页珍藏版)》请在冰豆网上搜索。
中间代码生成程序三地址
#include
#include
#include
usingnamespacestd;
stackstate;
stacksymbol;
//stackval;
stacksymbol2;
charsen[50];
charsym[12][6]={//符号表
{'s','e','e','s','e','e'},
{'e','s','e','e','e','a'},
{'r','r','s','r','r','r'},
{'r','r','r','r','r','r'},
{'s','e','e','s','e','e'},
{'r','r','r','r','r','r'},
{'s','e','e','s','e','e'},
{'s','e','e','s','e','e'},
{'e','s','e','e','s','e'},
{'r','r','s','r','r','r'},
{'r','r','r','r','r','r'},
{'r','r','r','r','r','r'}
};
charsnum[12][6]={//数字表
{5,1,1,4,2,1},
{3,6,5,3,2,0},
{2,2,7,2,2,2},
{4,4,4,4,4,4},
{5,1,1,4,2,1},
{6,6,6,6,6,6},
{5,1,1,4,2,1},
{5,1,1,4,2,1},
{3,6,5,3,11,4},
{1,1,7,1,1,1},
{3,3,3,3,3,3},
{5,5,5,5,5,5}
};
intgo2[12][3]={//goto表
{1,2,3},
{0,0,0},
{0,0,0},
{0,0,0},
{8,2,3},
{0,0,0},
{0,9,3},
{0,0,10},
{0,0,0},
{0,0,0},
{0,0,0},
{0,0,0}
};
voidaction(inti,char*&a,char&how,int&num,char&A,int&b,int&k)//action函数[i,a]
{
intj;//,r;
chars1,s2,s3;
charv;
switch(*a)
{
case'i':
//case'd':
j=0;break;
case'+':
j=1;break;
case'*':
j=2;break;
case'(':
j=3;break;
case')':
j=4;break;
case'#':
j=5;break;
default:
j=-1;break;
}
if(j!
=-1)
{
how=sym[i][j];
num=snum[i][j];
if(how=='r')
{
switch(num)
{
case1:
A='E',b=3;
cout<<"按E->E1+T规约"<s1=symbol2.top();symbol2.pop();s2=symbol2.top();symbol2.pop();
s3=symbol2.top();symbol2.pop();symbol2.push(k+48);
cout<<"t"<'t':
'')<'t':
'')<k++;
break;
case2:
A='E',b=1;
cout<<"按E->T规约"<break;
case3:
A='T',b=3;
cout<<"按T->T1*F规约"<s1=symbol2.top();symbol2.pop();s2=symbol2.top();symbol2.pop();
s3=symbol2.top();symbol2.pop();symbol2.push(k+48);
cout<<"t"<'t':
'')<'t':
'')<k++;
break;
case4:
A='T',b=1;
cout<<"按T->F规约"<break;
case5:
A='F',b=3;
cout<<"按F->(E)规约"<break;
case6:
A='F',b=1;
cout<<"按F->id规约"<break;
default:
break;
}
}
}
}
intgo(intt,charA)//goto[t,A]
{
switch(A)
{
case'E':
returngo2[t][0];break;
case'T':
returngo2[t][1];break;
case'F':
returngo2[t][2];break;
}
}
voiderror(inti,intj,char*&a)//error显示函数
{
cout<<"error"<switch(j)
{
case1:
//期望输入id或左括号,但是碰到+,*,或$,就假设已经输入id了,转到状态5
//state.push(5);
//symbol.push('i');//必须有这个,如果假设输入id的话,符号栈里必须有....
cout<<"缺少运算对象digit"<break;
case2:
//从输入中删除右括号
//a++;
cout<<"不配对的右括号"<break;
case3:
//期望碰到+,但是输入id或左括号,假设已经输入算符+,转到状态6
//state.push(6);
//symbol.push('+');
cout<<"缺少运算符"<break;
case4:
//缺少右括号,假设已经输入右括号,转到状态11
//state.push(11);
//symbol.push(')');
cout<<"缺少右括号"<break;
case5:
//a++;
cout<<"*号无效,应该输入+号!
"<//case6:
//a++;
}
}
intmain()
{
ints;
char*a;
charhow;
intnum;
intb;
charA;
intk=1;
charq;
while
(1)
{
cin>>sen;
a=sen;
state.push(0);//先输入0状态
while(*a!
='\0')
{
b=0;num=0;how='\0';A='\0';
s=state.top();
q=*a;
if(isalpha(*a))
{
*a='i';
}
action(s,a,how,num,A,b,k);
if(how=='s')//移进
{
cout<<"移进"<symbol.push(*a);
state.push(num);
if(q!
='('&&q!
=')')
{
symbol2.push(q);
}
a++;
}
elseif(how=='r')//规约
{
for(inti=0;i
{
if(!
state.empty())
state.pop();
if(!
symbol.empty())
symbol.pop();
}
intt=state.top();
symbol.push(A);
state.push(go(t,A));
}
elseif(how=='a')//接受
{
cout<<"成功接受"<break;
}
else
{
error(s,num,a);//错误显示
cout<<"输入有误,重新输入!
"<break;
}
}
}
return0;
}