1、编译原理课程设计项目计算机科学系课程设计任务书题 目: 简单编译器的设计与实现 姓 名: 学 号: 年 级: 专 业: 计算机科学与技术 指导教师: 职 称: 讲师 枣庄学院计算机科学系2010年12月2日课程设计的具体要求:在学习程序设计语言编译原理课程过程中,结合各章节构造编译程序的基本理论分别完成词法分析器、语法分析器和语义分析器实验,在基本实验完成的基础上,逐步完成课程设计。针对自己的理解和学习,实现一个小编译器包括符号表的构造,词法分析,语法分析,目标代码生成等重要子程序(其中词法分析、语法分析及语义分析功能必须完成),并对其进行分析解释和总结,同时将理论与实际应用结合起来,接受软件
2、设计等开发过程的全面训练,从而提高软件开发的能力。样本语言为C-语言,实现简单的编译器,其中基本的语句要求必须实现,其余部分可根据自己的实际情况选择实现。对主要代码给予解释和理解注释,各函数和过程应有简要描述,有功能说明,有入口和出口参数说明。 指导教师:_ 时间:_指导教师评语:成绩:_ 指导教师:_ 时间:_所需实验环境、设备: Windows XP操作系统、WIN-TC操作平台课程设计的具体安排: 2010年11月20日2010年11月22日,整理资料,准备材料 2010年11月23日2010年11月25日,编写代码,实现功能 2010年11月26日2010年11月30日,调试,修改,完
3、善 2010年11月31日,上交作业老师验收。 参考文献:1程序设计语言编译原理,陈火旺编著,国防工业出版社2编译原理,吕映芝、张素琴、蒋维杜编著,清华大学出版社3编译原理,Alfred V.Aho等,李建中译,机械工业出版社 简单编译器的设计与实现一、 课程设计的目的 在学习程序设计语言编译原理课程过程中,结合各章节构造编译程序的基本理论分别完成词法分析器、语法分析器和语义分析器实验,在基本实验完成的基础上,逐步完成课程设计。针对自己的理解和学习,实现一个小编译器括符号表的构造,词法分析,语法分析,目标代码生成等重要子程序,其中词法分析、语法分析及语义分析功能必须完成),并对其进行分析解释和
4、总结,同时将理论与实际应用结合起来,接受软件设计等开发过程的全面训练,从而提高软件开发的能力。二、 课程设计的任务(1)设计符号表确定符号表的组织方式,一般应包括名字栏和信息栏,其中名字栏作为关键字。要考虑能够存储有关名字的信息,并可以高效地完成如下操作:a.查找:根据给定的名字,在符号表中查找其信息。如果该名字在符号表中不存在,则将其加入到符号表中,否则返回指向该名字的指针;b.删除:从符号表中删除给定名字的表项。(2)设计词法分析器设计各单词的状态转换图,并为不同的单词设计种别码。将词法分析器设计成供语法分析器调用的子程序。功能包括:a. 具备预处理功能。将不翻译的注释等符号先滤掉,只保留
5、要翻译的符号串,即要求设计一个供词法分析调用的预处理子程序;b. 能够拼出语言中的各个单词;c. 将拼出的标识符填入符号表;d. 返回(种别码, 属性值)。(3)语法分析器要求用预测分析法、递归下降分析法、算符优先分析法、SLR分析法(几种方法任选),实现对表达式、各种说明语句、控制语句进行语法分析。(4)目标代码生成器能完成指定寄存器个数的情况下将一中间代码程序段翻译成汇编语言目标代码(汇编指令应包括加、减、乘、除),要求指令条数最少的情况下,尽量使用寄存器,尽量少访问内存,这样才能做到运行效率高。三、课程设计要求样本语言为C-语言,实现简单的编译器,其中基本的语句要求必须实现,其余部分可根
6、据自己的实际情况选择实现。对主要代码给予解释和理解注释,各函数和过程应有简要描述,有功能说明,有入口和出口参数说明。四、 简单编译器的实现流程图源程序 单词符号 语法单位 中间代码 中间代码 目标代码 五、 实现环境Windows XP操作系统、win-TC运行环境六、课程设计的详细过程(1) 设计词法分析器设计思想:要求:1. 对单词的构词规则有明确的定义;2. 编写的分析程序能够正确识别源程序中的单词符号;3. 识别出的单词以的形式保存在符号表中;4. 词法分析中源程序的输入以.c格式,分析后的符号表保存在.txt文件中。5. 对于源程序中的词法错误,能够做出简单的错误处理,给出简单的错误
7、提示,保证顺利完成整个源程序的词法分析;6. 输入:由符合规定单词类别结构的各类单词组成的源程序。实现方法:根据加入语义过程的状态转换图直接编写词法分析程序。根据每一组状态转换关系(标识符)组织程序结构,并将所有公共处理过程分别实现即可。在扫描源程序字符串时,一旦识别出关键字、运算符、标识符、无符号常数中之一,即以二元式形式(类别编码,值)输出单词。每次调用词法分析程序,它均能自动继续扫描下去,形成下一个单词。实现过程及主要代码:定义主要函数: char prog80=0, token8; char ch;int syn,n,sum,m,p; char *rwtab6=begin,if,the
8、n,while,do,end;实现函数代码:扫描功能:void scaner() m=0;sum=0; for(n=0;n8;n+) tokenn=0;ch=progp+; while(ch= ) ch=progp+; if(isalpha(ch) while(isalpha(ch)|isdigit(ch) tokenm+=ch; ch=progp+; tokenm+=0; ch=progp-; syn=10; for(n=0;n6;n+) if(strcmp(token,rwtabn)=0) syn=n+1;break; Else if(isdigit(ch) while(isdigit(c
9、h) sum=sum*10+ch-0; ch=progp+; ch=progp-; syn=11; else switch(ch) case:m=0;tokenm+=ch;ch=progp+; if(ch=) syn=24; tokenm+=ch; else syn=23; ch=progp-; break; case:m=0;tokenm+=ch;ch=progp+; if(ch=) syn=18; tokenm+=ch; else syn=17; ch=progp-; break; case+:syn=13;token0=ch;break; case-:syn=14;token0=ch;b
10、reak; case*:syn=15;token0=ch;break; case/:syn=16;token0=ch;break; case=:syn=25;token0=ch;break; case;:syn=26;token0=ch;break; case(:syn=27;token0=ch;break; case):syn=28;token0=ch;break; case#:syn=0;token0=ch;break; default:syn=-1;主函数:main() printf(nnThe significance of the figures:n 1.figures 1 to 6
11、 said Keywordn 2.figures 10 and 11 said Other indicatorsn 3.figures 13 to 28 said Operatorsn); p=0;printf(nplease input string:n); do ch=getchar(); progp+=ch; while(ch!=#);p=0;do scaner(); switch(syn)case 11: printf(%d,%d)n,syn,sum);break;case -1: printf(n ERROR;n);break;default: printf(%d,%s)n,syn,
12、token); while(syn!=0); getch();(2)设计语法、语义分析器设计思想:要求:1. 对语法规则有明确的定义;2. 编写的分析程序能够对实验一的结果进行正确的语法分析;3编写的分析程序能够对实验二的结果进行正确的语义分析;4对于遇到的语法、语义错误,能够做出简单的错误处理,给出简单的错误提示,保证语义分析过程;实现方法: 在词法分析识别出单词符号的基础上分析并规定程序的语法结构是否符合语法规则。其工作本质就是按文法的产生式,识别输入符号串是否为一个句子。首先定义语法规则,然后按照规则实现语法分析。实现过程及主要代码: 插入符号表动作name-defn, t的程序如下:i
13、nt name_def(char *name) int i,es=0; if (fhbp=maxfhbp) return(-1); for(i=fhbp-1;i=0;i-)/查符号表 if (strcmp(fhbi.name,name)=0) es=21;/21表示变量重复声明 break; if (es=21) return(es); strcpy(fhbfhbp.name,name); fhbfhbp.address=datap; datap+;/分配一个单元,数据区指针加1 fhbp+; return(es); 查询符号表返回地址:int lookup(char *name,int *p
14、address) int i,es=0; for(i=0;ifhbp;i+) if (strcmp(fhbi.name,name)=0) *paddress=fhbi.address; return(es); es=23;/变量没有声明 return(es); 语法、语义分析及代码生成程序:int TESTparse() int es=0;if(fp=fopen(bbb.t,r)=NULL) printf(n打开%s错误!n,Scanout); es=10;return(es); /printf(请输入目标文件名(包括路径):); /scanf(%s,Codeout); if(fout=fop
15、en(ccc.t,w)=NULL) printf(n创建%s错误!n,Codeout); es=10; return(es); if (es=0) es=program(); printf(=语法、语义分析及代码生成程序结果=n); switch(es) case 0: printf(语法、语义分析成功并抽象机汇编生成代码!n);break; case 10: printf(打开文件 %s失败!n,Scanout);break; case 1: printf(缺少!n);break; case 2: printf(缺少!n);break; case 3: printf(缺少标识符!n);bre
16、ak; case 4: printf(少分号!n);break; case 5: printf(缺少(!n);break; case 6: printf(缺少)!n);break; case 7: printf(缺少操作数!n);break; case 21: printf(符号表溢出!n);break; case 22: printf(变量重复定义!n);break; case 23: printf(变量未声明!n);break; fclose(fp); fclose(fout);return(es); 定义语义规则并实现::=program:=int program() int es=0,
17、i; fscanf(fp,%s %sn,token,token1); printf(%s %sn,token,token1); if(strcmp(token,) /判断是否 es=1; return(es); fscanf(fp,%s %sn,&token,&token1); printf(%s %sn,token,token1); es=declaration_list(); if (es0) return(es); printf( 符号表n); printf( 名字 地址n); for(i=0;i0) return(es); if(strcmp(token,)/判断是否 es=2; re
18、turn(es); fprintf(fout, STOPn);/产生停止指令 return(es);:=|/:=/|/改成:=int declaration_list() int es=0; while (strcmp(token,int)=0) es=declaration_stat(); if (es0) return(es); return(es); :=int ;/fhbp,datap,codep -int IDnname-defn,t;int declaration_stat() int es=0; fscanf(fp,%s %sn,&token,&token1);printf(%s
19、 %sn,token,token1); if (strcmp(token,ID) return(es=3); /不是标识符 es=name_def(token1);/插入符号表 if (es0) return(es); fscanf(fp,%s %sn,&token,&token1);printf(%s %sn,token,token1); if (strcmp(token,;) ) return(es=4); fscanf(fp,%s %sn,&token,&token1);printf(%s %sn,token,token1); return(es);:=|/:=|/改成:=int sta
20、tement_list() int es=0; while (strcmp(token,) es=statement(); if (es0) return(es); return(es); :=|/ |/:= |/ | |int statement() int es=0; if (es=0 & strcmp(token,if)=0) es=if_stat();/ if (es=0 & strcmp(token,while)=0) es=while_stat();/ if (es=0 & strcmp(token,for)=0) es=for_stat();/ /可在此处添加do语句调用 if
21、(es=0 & strcmp(token,read)=0) es=read_stat();/ if (es=0 & strcmp(token,write)=0) es=write_stat();/ if (es=0 & strcmp(token,)=0) es=compound_stat();/ if (es=0 & (strcmp(token,ID)=0|strcmp(token,NUM)=0) es=expression_stat();/ return(es); := if () else /:= if () else if ()BRFlabel1 BRlabel2 SETlabellab
22、el1 else SETlabellabel2if ()BRFlabel1 BRlabel2 SETlabellabel1 else SETlabellabel2其中动作符号的含义如下 BRFlabel1 :输出 BRF label1, BRlabel2:输出 BR label2, SETlabellabel1:设置标号label1 SETlabellabel2:设置标号label2int if_stat() int es=0,label1,label2; /if fscanf(fp,%s %sn,&token,&token1); printf(%s %sn,token,token1); if
23、 (strcmp(token,() return(es=5); /少左括号 fscanf(fp,%s %sn,&token,&token1); printf(%s %sn,token,token1); es=expression(); if (es0) return(es); if (strcmp(token,) return(es=6); /少右括号 label1=labelp+;/用label1记住条件为假时要转向的标号 fprintf(fout, BRF LABEL%dn,label1);/输出假转移指令 fscanf(fp,%s %sn,&token,&token1); printf(
24、%s %sn,token,token1); es=statement(); if (es0) return(es); label2=labelp+;/用label2记住要转向的标号fprintf(fout, BR LABEL%dn,label2);/输出无条件转移指令fprintf(fout,LABEL%d:n,label1);/设置label1记住的标号 if (strcmp(token,else)=0)/else部分处理 fscanf(fp,%s %sn,&token,&token1); printf(%s %sn,token,token1); es=statement(); if (es0) return(es); fprintf(fout,LABEL%d:n,label2);/设置label2记住的标号 return(es); :=while() /:= while () /*:=while SETlabellabel1() BRFlabel2 BRlabel1 SETlabellabel2:=while SETlabellabel1() BRFlabel2 BRlabel1 SETlabellabel2动作解释如下:SETlabellabel1:设置标号label1BRFlabel2 :输出 B
copyright@ 2008-2022 冰豆网网站版权所有
经营许可证编号:鄂ICP备2022015515号-1