编译原理实验报告实验一编写词法分析程序
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
编译原理实验报告实验名称:实验一编写词法分析程序
实验类型:验证型实验
指导教师:何中胜
专业班级:13软件四
姓名:丁越
学号:
电子邮箱:
实验地点:秋白楼B720
实验成绩:
日期:2016年3 月18 日
一、实验目的
通过设计、调试词法分析程序,实现从源程序中分出各种单词的方法;熟悉词法分析
程序所用的工具自动机,进一步理解自动机理论。掌握文法转换成自动机的技术及有穷自动机实现的方法。确定词法分析器的输出形式及标识符与关键字的区分方法。加深对课堂教学的理解;提高词法分析方法的实践能力。通过本实验,应达到以下目标:
1、掌握从源程序文件中读取有效字符的方法和产生源程序的内部表示文件的方法。
2、掌握词法分析的实现方法。
3、上机调试编出的词法分析程序。
二、实验过程
以编写PASCAL子集的词法分析程序为例
1.理论部分
(1)主程序设计考虑
主程序的说明部分为各种表格和变量安排空间。
数组 k为关键字表,每个数组元素存放一个关键字。采用定长的方式,较短的关键字
后面补空格。
P数组存放分界符。为了简单起见,分界符、算术运算符和关系运算符都放在 p表中
(编程时,还应建立算术运算符表和关系运算符表,并且各有类号),合并成一类。
id和ci数组分别存放标识符和常数。
instring数组为输入源程序的单词缓存。
outtoken记录为输出内部表示缓存。
还有一些为造表填表设置的变量。
主程序开始后,先以人工方式输入关键字,造 k表;再输入分界符等造p表。
主程序的工作部分设计成便于调试的循环结构。每个循环处理一个单词;接收键盘上
送来的一个单词;调用词法分析过程;输出每个单词的内部码。
⑵词法分析过程考虑
将词法分析程序设计成独立一遍扫描源程序的结构。其流程图见图1-1。
图1-1
该过程取名为 lexical,它根据输入单词的第一个字符(有时还需读第二个字符),判断单词类,产生类号:以字符 k表示关键字;i表示标识符;c表示常数;p表示分界符;s表示运算符(编程时类号分别为 1,2,3,4,5)。
对于标识符和常数,需分别与标识符表和常数表中已登记的元素相比较,如表中已有
该元素,则记录其在表中的位置,如未出现过,将标识符按顺序填入数组id中,将常数
变为二进制形式存入数组中 ci中,并记录其在表中的位置。
lexical过程中嵌有两个小过程:一个名为getchar,其功能为从instring中按顺序取出一个字符,并将其指针pint加1;另一个名为error,当出现错误时,调用这个过程,
输出错误编号。
2.实践部分
所有识别出的单词都用两个字节的等长表示,称为内部码。第一个字节为t,第二个字节为i。t为单词的种类。关键字的t=1;分界符的 t=2;算术运算符的t=3;关系运算符的t=4;无符号数的t=5;标识符的 t=6。i为该单词在各自表中的指针或内部码值。表 1-1为关键字表;表1-2为分界符表;表1-3为算术运算符的i
表1-4
常数表和标识符表是在编译过程中建立起来的。其 i值是根据它们在源程序中出现的顺序确定的。另外可以根据Pascal语言子集中出现其它单词情况进行自行修改以上表格。
最后编写程序进行词法分析,判断目标在哪个表中并进行显示。
三、实验结果
1.测试数据
数据共分为3组,分别如下:
第一组数据
var i,j,k:integer;
begin
i:=5;
j:=6;
k:=i+j;
write("k=",k);
End.
第二组数据
var i,sum:integer;
begin
sum:=0;
for i:=1 to 10 do
begin
sum:=sum+i;
end;
writeln("sum=",sum);
End.
第三组数据
var weight,price:real;
begin
write("please input weight: ");
readln(weight);
if weight<10
then
price=5;
else
price=5+(weight-10)*;
writeln("price=",price);
End.
这三组数据都是通过文件“”读入到程序中,通过程序一一读取文件中的数据进行分析,程序分析时要注意所属的类型。
2.测试结果
以上三组数据测试结果通过控制台显示,显示时要根据表进行分类,不同的表有不同的标号,具体显示如图1-1,1-2,1-3,和1-4所示:
第一组数据
图1-2
第二组数据
图1-3
第三组数据
图1-4
图1-4(接图1-5)
四、讨论与分析
实验结果的每一条数据可分为两个部分。第一个部分是识别出的单词部分,第二个部分(小括号内的部分)则显示了单词在表中的位置,括号内第一个数字表示是第几张表,第二个数字代表单词在表的位置。
实验结果与预期结果一致。
该实验证明了通过其他语言来编译一种语言的词法分析器是可行的。
实验结果说明了词法分析是作为相对独立的阶段来完成的。在词法分析过程中,编译程序是通过操作系统从外部介质中读取源程序文件中的各个字符的。同时,为正确地识别单词,有时还需进行超前搜索和回退字符等操作。
因此,为了提高读盘效率和便于扫描器进行工作,通常可采用缓冲输入的方案,即在内存中设置一个适当大小的输入缓冲区,让操作系统直接将磁盘上的源程序字符串分批送入此缓冲区中,供扫描器进行处理。
五、附录:
关键代码部分如下:
bool isKey( string str, int &syn) /*判断是否为关键字,若是传回相应关键码的种别名*/
{
int i;
for(i=0; i<7; i++)
{
if(str == key[i])
{
syn = i + 1;