编译技术课程设计A.docx
《编译技术课程设计A.docx》由会员分享,可在线阅读,更多相关《编译技术课程设计A.docx(21页珍藏版)》请在冰点文库上搜索。
编译技术课程设计A
科技学院
课程设计报告
(2013--2014年度第1学期)
名称:
编译技术课程设计A
院系:
班级:
学号:
学生姓名:
指导教师:
设计周数:
2
成绩:
《编译技术课程设计A》
任务书
一、目的与要求
1.理解和掌握编译程序设计原理及常用的技术,建立编译程序的整体概念;
2.理解和掌握编译程序词法分析、语法分析、语义分析、中间代码生成和目标代码生成等几个关键环节原理和实现算法;
3.掌握软件模块设计技能;熟悉并能较好地利用软件开发环境独立编程、调试和分析程序运行情况,逐渐形成创新思维和从事系统软件的研究和开发能力。
二、主要内容
定义一个简化的类C语言—L语言作为源语言,重点针对词法分析、语法分析、语义分析、中间代码生成和目标代码生成等几个关键环节进行编程和调试训练,最终设计实现L语言的编译程序。
通过调试L编译程序,了解一般编译程序的总体框架,掌握编译各阶段程序的构造,理解和掌握错误处理方法及符号表的组织方式,理解和掌握语法制导翻译方法。
还可以适当扩展L语言成分,并对相应的编译程序进行扩充。
可使用C、VC++等语言编程实现。
具体内容包括:
1.由单词的语法规则出发、画出识别单词的状态转换图,然后用程序实现扫描器设计。
2.设计、编写和调试算法优先分析程序,了解算法优先分析器的组成结构以及对文法的要求,掌握实现通用算法优先分析算法的方法。
3.在算符优先分析文法的基础上进行翻译工作,生成四元式表;
4.设计一个简单的代码生成器,该代码生成器以基本块为单位,依次将每条中间代码变换成相应的目标代码。
5.综合以上实验的结果,并进行集成与设计,开发出一个小型编译程序。
对于各项主要内容的实现细节描述和指导,请参考《计算机综合实践指导》编译技术的相关内容。
三、进度计划
序号
设计(实验)内容
完成时间
备注
1
词法分析器设计
2天
2
算符优先分析程序设计
3天
3
语法制导翻译程序设计
3天
4
简单代码生成器设计
2天
四、设计(实验)成果要求
至少完成简单变量定义语句及包含算术运算符的赋值语句的整个编译过程,统一使用课程设计报告书,文字清楚、工整。
五、考核方式
实验结果(60%)+实验报告(30%)+实验过程表现(10%)
学生姓名:
指导教师:
年月日
实验一.词法分析器的设计与实现
一、实验目的
(1)掌握C语言单词符号的划分、正规式、状态转换图及词法分析器的实现。
(2)掌握词法分析程序的作用。
二、实验要求
(1)对任给的一个C语言源程序,能够虑掉空格、回车换行符、tab键及注释。
(2)识别各类单词符号,如关键字、标识符、运算符、常数、界符,结果以二元式形式输出,并构造符号表。
(3)输出有词法错误的单词及所在行号。
(在此阶段只能识别有限的词法错误)
1、各种单词符号对应的种别码
单词符号
种别码
单词符号
种别码
begin
1
:
17
if
2
:
=
18
then
3
>
20
while
4
<>
21
do
5
<=
22
end
6
<
23
letter(letter|digit)*
10
>=
24
digitdigit*
11
=
25
*
13
;
26
/
14
(
27
+
15
)
28
-
16
#
0
2、词法分析程序的功能
输入:
所给文法的源程序字符串。
输出:
二元组(syn,token或sum)构成的序列。
其中:
syn为单词种别码;
token为存放的单词自身字符串;
sum为整型常数。
三、源程序代码:
#include
#include
#include
charprog[80],token[8];
charch;
intsyn,p,m=0,n,row,sum=0;
char*rwtab[7]={"int","begin","if","then","while","do","end"};
intk;
voidscaner()
{
/*
共分为三大块,分别是标示符、数字、符号,对应下面的ifelseif和else
*/
for(n=0;n<8;n++)token[n]=NULL;
ch=prog[p++];
while(ch=='')//剔除空格
{
ch=prog[p];
p++;
}
if((ch>='a'&&ch<='z')||(ch>='A'&&ch<='Z'))
{
m=0;
while((ch>='0'&&ch<='9')||(ch>='a'&&ch<='z')||(ch>='A'&&ch<='Z'))//如:
a1
{
token[m++]=ch;
ch=prog[p++];
}
token[m++]='\0';
p--;
syn=10;
for(n=0;n<6;n++)
if(strcmp(token,rwtab[n])==0)
{
k=n;
syn=n+1;
break;
}
}
elseif((ch>='0'&&ch<='9'))
{
{
sum=0;
while((ch>='0'&&ch<='9'))
{
sum=sum*10+ch-'0';//chascii
ch=prog[p++];
}
}
p--;//同上
syn=11;
if(k==0)//int
if(sum>65535)
syn=-1;
}
elseswitch(ch)
{
case'<':
m=0;token[m++]=ch;
ch=prog[p++];
if(ch=='>')//判断是不是<>
{
syn=21;
token[m++]=ch;
}
elseif(ch=='=')//---------------<=
{
syn=22;
token[m++]=ch;
}
else
{
syn=23;
p--;
}
break;
case'>':
m=0;token[m++]=ch;
ch=prog[p++];
if(ch=='=')//----------------->=
{
syn=24;
token[m++]=ch;
}
else
{
syn=20;
p--;
}
break;
case':
':
m=0;token[m++]=ch;
ch=prog[p++];
if(ch=='=')//------------------:
=
{
syn=18;
token[m++]=ch;
}
else
{
syn=17;
p--;
}
break;
case'*':
syn=13;token[0]=ch;break;
case'/':
syn=14;token[0]=ch;break;
case'+':
syn=15;token[0]=ch;break;
case'-':
syn=16;token[0]=ch;break;
case'=':
syn=25;token[0]=ch;break;
case';':
syn=26;token[0]=ch;break;
case'(':
syn=27;token[0]=ch;break;
case')':
syn=28;token[0]=ch;break;
case'#':
syn=0;token[0]=ch;break;//程序结束
case'\n':
syn=-2;break;
default:
syn=-1;break;
}
}
intmain()
{
p=0;
row=1;
cout<<"Pleaseinputstring:
"<do
{
cin.get(ch);//输入
prog[p++]=ch;
}
while(ch!
='#');//当输入#结束输入
p=0;//p指针清零
do
{
scaner();
switch(syn)
{
case11:
cout<<"("<case-1:
cout<<"Errorinrow"<"<case-2:
row=row++;break;
default:
cout<<"("<}
}while(syn!
=0);
return0;
}
四、结果验证
1、给定源程序
ifa=13;intb=4;#
输出结果
2、源程序(包括上式未有的while、do以及判断错误语句):
while
b>=13
begin
a<*
#
输出结果
实验二.语法分析器的设计与实现
一、课程设计(综合实验)的目的与要求
2.1算符优先分析程序设计的实验目的
本实验是为计算机科学与技术专业的学生在学习《编译技术》课程后,为加深对课堂教学内容的理解,培养解决实际问题能力而设置的实践环节。
通过这个实验,使学生应用编译程序设计的原理和技术,设计、编写和调试算符优先分析程序,了解算符优先分析程序的组成结构,掌握实现通用算符优先分析算法的方法。
能使得学生在设计和调试编译程序的能力方面有所提高。
为将来设计、分析编译程序打下良好的基础。
2.2算符优先分析程序设计的实验要求
算符优先分析属于自下而上的分析方法,该语法分析程序的输入是终结符号串(即单词符号串,以一个“
”结尾),如果输入串是句子则输出“YES”,否则输出“NO”和错误信息。
算符优先分析过程与非终结符号无关,当由文法产生了优先关系之后文法也就失去了作用,本题目给出文法的目的是为了便于对语法分析结果进行验证。
(1)文法 设算符优先文法
为:
说明:
i为整型常数或者为标识符表示整型变量;使用中↑用**表示。
(2)优先关系表 设优先关系表如表1-2所示。
表1-2 优先关系表
+
*
i
(
)
#
+
*
i
(
)
#
二、设计(实验)正文
1.算符优先分析流程图
2.程序代码
#include
charVt[7]={'+','*','-','i','(',')','#'};
//+*-i()#
intQ[7][7]={3,2,2,2,2,3,3,//+
3,3,2,2,2,3,3,//*
3,3,2,2,2,3,3,//-
3,3,3,4,4,3,3,//i
2,2,2,2,2,0,4,//(
3,3,3,4,4,3,3,//)
2,2,2,2,2,4,0};//#表示算符优先级3:
大于2:
小于0:
等于
intisVt(chara)//判断是不是终结符
{
for(intp=0;p<7;p++)
{
if(Vt[p]==a)
return1;
}
return0;
}
intdayu(chara,charb)//优先级a>b
{
intm,n;
for(intp=0;p<7;p++)
{
if(Vt[p]==a)
{
m=p;
}
if(Vt[p]==b)
{
n=p;
}
}
if(Q[m][n]==3)
{
return1;
}
elsereturn0;
}
intxiaoyu(chara,charb)//优先级a
{
intm,n;
for(intp=0;p<7;p++)
{
if(Vt[p]==a)
{
m=p;
}
if(Vt[p]==b)
{
n=p;
}
}
if(Q[m][n]==2)
{
return1;
}
elsereturn0;
}
intdengyu(chara,charb)//优先级a=b
{
intm,n;
for(intp=0;p<7;p++)
{
if(Vt[p]==a)
{
m=p;
}
if(Vt[p]==b)
{
n=p;
}
}
if(Q[m][n]==0)
{
return1;
}
elsereturn0;
}
intmain()
{
chartemp[50]={'/0'},ch;
cout<<"请输入表达式串(以#号结束):
";
intn=0;
do{
cin.get(ch);
temp[n]=ch;
n++;
}while(ch!
='#');
cout<<"规约过程"<cout<<"堆栈剩余串说明"<intk=1,p=0,j;
chars[50],q,a;
s[k]='#';
cout<
cout<cout<<"移近"<do
{
inth;
a=temp[p];
p++;
if(isVt(s[k]))
j=k;
else
j=k-1;
while(dayu(s[j],a)==1)
{
do
{
q=s[j];
if(isVt(s[j-1]))
j=j-1;
else
j=j-2;
}while(xiaoyu(s[j],q)!
=1);
k=j+1;
s[k]='N';
for(h=1;h<=k;h++)
{
cout<
}
cout<<"";
for(h=(p-1);h{
cout<}
cout<<""<<"归约"<}
if(xiaoyu(s[j],a)||dengyu(s[j],a))
{
k=k+1;
s[k]=a;
for(h=1;h<=k;h++)
{
cout<
}
cout<<"";
for(h=p;h{
cout<}
cout<<""<<"移进"<}
else
{
cout<<"语法错误"<}
}while(a!
='#');
if(s[1]==s[3])
{
cout<<"归约成功,语法正确"<}
return0;
}
3.实验运行结果如下:
三、课程设计(综合实验)总结或结论
通过这次实验,以及本学期的上机实验的课程学习,加深了我对程序学习过程的理解,
同时学会了应用编译程序设计的原理和技术设计出词法分析器,了解了扫描器的组成结构,不同种类单词的识别方法。
虽然好多程序代码都不是自己写的,但是通过读懂别人的代码也能学到好多东西。
通过老师的教导我学到了很多课堂上学不到的事,明白了无论遇到什么困难,都要有狠心有毅力。
四、参考文献
鲁斌编译原理基础教程清华大学出版社2011年10月第一版
赵建华1郑滔2编译原理(第二版)机械工程出版社2009年1月
|