编译原理词法分析器语法分析器实验报告Word格式.docx
- 文档编号:18641693
- 上传时间:2022-12-30
- 格式:DOCX
- 页数:24
- 大小:105.46KB
编译原理词法分析器语法分析器实验报告Word格式.docx
《编译原理词法分析器语法分析器实验报告Word格式.docx》由会员分享,可在线阅读,更多相关《编译原理词法分析器语法分析器实验报告Word格式.docx(24页珍藏版)》请在冰豆网上搜索。
$COMMA
$LPAR
$RPAR
-
内部字符串
标准二进形式
对于这个小语言,有几点重要的限制:
首先,所有的关键字(如IF﹑WHILE等)都是“保留字”。
所谓的保留字的意思是,用户不得使用它们作为自己定义的标示符。
例如,下面的写法是绝对禁止的:
IF(5)=x
其次,由于把关键字作为保留字,故可以把关键字作为一类特殊标示符来处理。
也就是说,对于关键字不专设对应的转换图。
但把它们(及其种别编码)预先安排在一张表格中(此表叫作保留字表)。
当转换图识别出一个标识符时,就去查对这张表,确定它是否为一个关键字。
再次,如果关键字、标识符和常数之间没有确定的运算符或界符作间隔,则必须至少用一个空白符作间隔(此时,空白符不再是完全没有意义的了)。
例如,一个条件语句应写为
IFi>
0i=1;
而绝对不要写成
IFi>
0i=1;
因为对于后者,我们的分析器将无条件地将IFI看成一个标识符。
这个小语言的单词符号的状态转换图,如下图:
2.语法分析器能识别由加+减-乘*除/乘方^括号()操作数所组成的算术表达式,其文法如下:
E→E+T|E-T|T
T→T*F|T/F|F
F→P^F|P
p→(E)|i
使用的算法可以是:
预测分析法;
递归下降分析法;
算符优先分析法;
LR分析法等。
3.中间代码生成器产生上述算术表达式的中间代码(四元式序列)
三、实现过程
给出各题目的详细算法描述,数据结构和函数说明,流程图。
1、词法分析器的流程图
2、语法分析器主程序图
3、中间代码生成器流程图:
四、源程序
词法分析器:
#include<
string.h>
malloc.h>
iostream>
usingnamespacestd;
typedefstructtable//分析表存储结构
{
charm[100];
}table;
tableM[100][100];
//定义分析表
typedefstructstacknode//定义栈内元素节点(带头结点(为空)的)
chardata;
structstacknode*next;
}stackk;
voidinitlink(stackk*&
s)//初始化新栈
{
s=(stackk*)malloc(sizeof(stackk));
s->
next=NULL;
}
voidpoplink(stackk*&
s)//顶元素出栈
stackk*p;
charv;
if(s->
next!
=NULL)
{
p=s->
next;
v=p->
data;
next=p->
}
free(p);
voidpushlink(stackk*&
s,charx)//新元素入栈
stackk*p;
p=(stackk*)malloc(sizeof(stackk));
p->
data=x;
next=s->
next=p;
voiddisplay(stackk*s)//打印现实显示栈内元素
inti=0,j;
charst[100];
while(p!
=NULL)
st[i++]=p->
p=p->
for(j=i-1;
j>
=0;
j--)
printf("
%c"
st[j]);
for(j=0;
j<
16-i;
j++)//打印对齐格式
'
'
);
chargettop(stackk*s)//返回栈顶元素值
next==NULL)
return0;
else
returns->
next->
intfind(charc,chararray[])//查找函数,
inti;
intflag=0;
for(i=0;
i<
100;
i++)
if(c==array[i])
flag=1;
returnflag;
intlocation(charc,chararray[])//定位函数,指出字符所在位置
returni;
voiderror()//出错函数定义
%15c出错!
\n"
voidanalyse(charVn[],charVt[])
inti,j,m,p,q,length,t,h;
charw,X;
charstr[100];
opt0:
scanf("
%s"
str);
for(i=0;
strlen(str);
{
if(!
find(str[i],Vt))
输入字符串有误!
请重新输入!
"
gotoopt0;
break;
}
stackk*st;
initlink(st);
pushlink(st,'
#'
pushlink(st,Vn[0]);
//#与识别符号入栈
j=0;
h=1;
w=str[0];
步骤%-12c分析栈%-24c剩余输入串%-12c所用产生式\n"
opt1:
%-16d"
h);
//显示步骤
h++;
display(st);
//显示分析栈中内容
X=gettop(st);
//上托栈顶符号放入X
poplink(st);
for(intk=0;
k<
14+j;
k++)//打印对齐格式
for(t=j;
t<
t++)
str[t]);
//显示剩余字符串
if(find(X,Vt)&
&
X!
='
)//分析栈的栈顶元素和剩余输入串的第一个元素相比较
if(X==w)
%15c匹配\n"
X);
j++;
w=str[j];
gotoopt1;
error();
if(X=='
if(X==w)
%8c是该文法的句子!
else
p=location(X,Vn);
q=location(w,Vt);
char*S1="
null"
*S2="
NULL"
;
if(strcmp(M[p][q].m,S1)==0||strcmp(M[p][q].m,S2)==0)//查找产生式
charstr0[100];
strcpy(str0,M[p][q].m);
%15c-->
%s\n"
X,str0);
//显示对应的产生式
if(strcmp(str0,"
$"
)==0)
length=strlen(str0);
//逆序进栈
for(m=length-1;
m>
m--)
pushlink(st,str0[m]);
intmain()
inti,k,n,r;
charVn[100],Vt[100],select;
******************************************************************\n"
对任意输入LL
(1)文法的分析表,判断验证字符串是否为该文法的句子\n"
并能给出分析和演示过程。
\n"
opt2:
请输入各终结符(#号表示结束)Vt[i]:
&
Vt[i]);
if(Vt[i]=='
r=i;
请输入非终结符个数:
%d"
n);
getchar();
for(i=0;
n;
请输入非终结符Vn[%d]:
i);
Vn[i]);
请输入此非终结符对应各终结符的产生式右部(null或NULL表示出错;
$表示空串):
for(k=0;
=r;
k++)
M[i][k].m);
opt3:
请输入要分析的字符串,且以#结束:
analyse(Vn,Vt);
********************请选择***********************\n"
1:
输入字符串\n"
2:
输入新分析表\n"
0:
退出\n"
*************************************************\n"
opt4:
cin>
>
select;
switch(select)
case'
1'
:
{gotoopt3;
break;
2'
{gotoopt2;
0'
{break;
default:
{printf("
输入错误!
请重新选择:
gotoopt4;
运行结果:
语法分析器源程序:
charprog[100],token[10];
charch;
intsyn,p,m=0,n,row,sum=0;
char*rwtab[20]={"
dim"
"
if"
do"
stop"
end"
"
and"
begin"
bool"
case"
char"
"
false"
for"
int"
not"
or"
set"
then"
true"
until"
while"
};
voidscaner()
for(n=0;
n<
9;
n++)token[n]=NULL;
ch=prog[p++];
while(ch=='
ch=prog[p];
p++;
if((ch>
a'
ch<
z'
)||(ch>
A'
Z'
))
m=0;
while((ch>
9'
{
token[m++]=ch;
ch=prog[p++];
}
token[m++]='
\0'
p--;
syn=21;
for(n=0;
20;
n++)
if(strcmp(token,rwtab[n])==0)
{
syn=n+1;
break;
}
elseif((ch>
sum=0;
while((ch>
sum=sum*10+ch-'
ch=prog[p++];
syn=7+15;
if(sum>
32767)
syn=-1;
elseswitch(ch)
case'
syn=8+15;
token[0]=ch;
+'
syn=9+15;
*'
token[m++]=ch;
ch=prog[p++];
if(ch=='
syn=11+15;
else
syn=10+15;
p--;
case'
syn=12+15;
('
syn=13+15;
)'
syn=14+15;
syn=0;
<
'
m=0;
token[m++]=ch;
if(ch=='
syn=17+15;
elseif(ch=='
syn=16+15;
syn=15+15;
syn=19+15;
syn=18+15;
syn=21+15;
syn=20+15;
/'
syn=22+15;
-'
syn=23+15;
syn=24+15;
default:
syn=-1;
voidmain()
p=0;
row=1;
cout<
endl<
endl;
***************************小型词法分析器**********************************"
请输入一段程序(以#结束):
do
cin.get(ch);
prog[p++]=ch;
while(ch!
**************************词法分析结果如下*********************************"
种别编码自身值"
scaner();
switch(syn)
case22:
("
syn<
"
sum<
)"
case-1:
"
Errorinrow"
row<
!
token<
while(syn!
=0);
中间代码生成器源程序:
表达式生成四元式
递归子程序法
string>
#include<
#defineDEFAULT_SIZE100
charEMachine(charw);
//表达式E的自动机
charTMachine(charw);
//表达式T的自动机
charFMachine(charw);
//表达式F的自动机
boolZMachine();
//表达式Z的自动机
stringintToString(inta);
//整形变成字符串形函数
classstack//栈类定义
private:
inttop;
string*stacka;
intmaxsize;
public:
stack(intsize=DEFAULT_SIZE);
~stack(){delete[]stacka;
voidpush(conststring&
item);
stringpop(void);
stringgettop(void)const;
boolempty(void)const{return(top==-1);
boolfull(void)const{return(top==maxsize-1);
voidclear(void){top=-1;
stack:
stack(intsize)//栈类的构造函数
top=-1;
maxsize=size;
stacka=newstring[maxsize];
stacka)
cerr<
allocatememoryfailed."
exit
(1);
voidstack:
push(conststring&
item)//压栈操作
if(full())
stackfull,cannotpush."
return;
top++;
stacka[top]=item;
stringstack:
pop(void)//出栈操作
if(empty())
stackempty,cannotpop."
exit
(1);
stringitem=stacka[top];
top--;
returnitem;
gettop(void)const//取栈顶操作
stackempty,cannotgettop."
returnstacka[top];
staticstackwordStack;
//符号栈
staticintnoOfQuet=0;
//静态四元式个数记录
staticintnoOfT=1;
//静态状态个数记录
voidmain(){//主函数
charyesOrNo;
//进行一个循环操作控制
do{
cout<
请输入算术表达式:
noOfT=1;
//每次结束询问
ZMachine();
Continue?
YesorNot:
cin>
yesOrNo;
//输入“Y”则继续
}while(yesOrNo=='
y'
//否则程序结束
boolZMachine(){//Z自动机
charw;
w;
w=EMachine(w);
//调用E自动机
if(w=='
){//遇到“#”则结束
returntrue;
else{
returnfalse;
charEMachine(charw){//E自动机
stringoperate,a,b,c;
stringstate[5];
w=TMachine(w);
//调用T自动机
while(w=='
||w=='
){//是加或减符号
operate=w;
//读入下一字符
w=TMachine(w);
//调用T自动机
b=wordStack.pop();
//字符栈弹出
a=wordStack.pop();
//两个操作字符
(\"
operate<
\"
a<
b<
t"
noOfT<
c="
t"
+intToString(noOfT);
//输出四元式
wordStack.
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 编译 原理 词法 分析器 语法 实验 报告