编译原理实验—语法分析器
编译原理实验报告
编译原理实验报告一、实验目的本次编译原理实验的主要目的是通过实践加深对编译原理中词法分析、语法分析、语义分析和代码生成等关键环节的理解,并提高实际动手能力和问题解决能力。
二、实验环境本次实验使用的编程语言为 C/C++,开发工具为 Visual Studio 2019,操作系统为 Windows 10。
三、实验内容(一)词法分析器的设计与实现词法分析是编译过程的第一个阶段,其任务是从输入的源程序中识别出一个个具有独立意义的单词符号。
在本次实验中,我们使用有限自动机的理论来设计词法分析器。
首先,我们定义了单词的种类,包括关键字、标识符、常量、运算符和分隔符等。
然后,根据这些定义,构建了相应的状态转换图,并将其转换为程序代码。
在实现过程中,我们使用了字符扫描和状态转移的方法,逐步读取输入的字符,判断其所属的单词类型,并将其输出。
(二)语法分析器的设计与实现语法分析是编译过程的核心环节之一,其任务是在词法分析的基础上,根据给定的语法规则,判断输入的单词序列是否构成一个合法的句子。
在本次实验中,我们采用了自顶向下的递归下降分析法来实现语法分析器。
首先,我们根据给定的语法规则,编写了相应的递归函数。
每个函数对应一种语法结构,通过对输入单词的判断和递归调用,来确定语法的正确性。
在实现过程中,我们遇到了一些语法歧义的问题,通过仔细分析语法规则和调整函数的实现逻辑,最终解决了这些问题。
(三)语义分析与中间代码生成语义分析的任务是对语法分析所产生的语法树进行语义检查,并生成中间代码。
在本次实验中,我们使用了四元式作为中间代码的表示形式。
在语义分析过程中,我们检查了变量的定义和使用是否合法,类型是否匹配等问题。
同时,根据语法树的结构,生成相应的四元式中间代码。
(四)代码优化代码优化的目的是提高生成代码的质量和效率。
在本次实验中,我们实现了一些基本的代码优化算法,如常量折叠、公共子表达式消除等。
通过对中间代码进行分析和转换,减少了代码的冗余和计算量,提高了代码的执行效率。
编译原理语法分析试验报告
编译原理语法分析试验报告语法分析是编译原理中的重要内容之一,主要用于对源程序进行语法检查,判断其是否符合给定的语法规则。
本次试验通过使用ANTLR工具,对C语言的子集进行了语法分析的实现。
一、实验目的:1.了解语法分析的基本概念和方法;2.使用ANTLR工具生成语法分析器;3.掌握ANTLR工具的基本使用方法;4.实现对C语言子集的语法分析。
二、实验内容:本次试验主要内容是使用ANTLR工具生成C语言子集的语法分析器,并对给定的C语言子集进行语法分析。
三、实验步骤:1.学习ANTLR工具的基本概念和使用方法;2.根据C语言子集的语法规则,编写ANTLR的语法文件(.g文件);3.使用ANTLR工具生成语法分析器;4.编写测试代码,对给定的C语言子集进行语法分析。
四、实验结果:经过以上的步骤,得到了一个完整的C语言子集的语法分析器,并且通过测试代码对给定的C语言子集进行了语法分析。
五、实验总结:通过本次实验,我对语法分析有了更深入的了解,掌握了使用ANTLR工具生成语法分析器的基本方法,同时也巩固了对C语言的基本语法规则的理解。
在实验过程中,遇到了一些问题,例如在编写ANTLR的语法文件时,对一些特殊语法规则的处理上有些困惑,但通过查阅资料和与同学的探讨,最终解决了这些问题。
本次试验对于我的学习有很大的帮助,我了解到了编译原理中的重要内容之一,也更深入地理解了语法分析的基本原理和方法。
通过实验,我发现使用ANTLR工具能够更方便地生成语法分析器,大大提高了开发效率。
总之,本次试验让我对编译原理中的语法分析有了更深入的了解,并且提高了我的编程能力和分析问题的能力。
在今后的学习和工作中,我将继续深入研究编译原理相关的知识,并应用到实际项目中。
国开电大 编译原理 实验4:语法分析实验报告
国开电大编译原理实验4:语法分析实
验报告
1. 实验目的
本实验的目的是研究和掌握语法分析的原理和实现方法。
2. 实验内容
本次实验主要包括以下内容:
- 设计并实现自顶向下的LL(1)语法分析器;
- 通过语法分析器对给定的输入串进行分析,并输出相应的分析过程;
- 编写测试用例,验证语法分析器的正确性。
3. 实验步骤
3.1 设计LL(1)文法
首先,根据实验要求和给定的语法规则,设计LL(1)文法。
3.2 构建预测分析表
根据所设计的LL(1)文法,构建预测分析表。
3.3 实现LL(1)语法分析器
根据预测分析表,实现自顶向下的LL(1)语法分析器。
3.4 对输入串进行分析
编写程序,通过LL(1)语法分析器对给定的输入串进行分析,并输出相应的分析过程和结果。
3.5 验证语法分析器的正确性
设计多组测试用例,包括正确的语法串和错误的语法串,验证语法分析器的正确性和容错性。
4. 实验结果
经过实验,我们成功设计并实现了自顶向下的LL(1)语法分析器,并对给定的输入串进行了分析。
实验结果表明该语法分析器具有较好的准确性和容错性。
5. 实验总结
通过本次实验,我们对语法分析的原理和实现方法有了更深入的了解。
同时,我们也学会了如何设计并实现自顶向下的LL(1)语
法分析器,并验证了其正确性和容错性。
这对于进一步研究编译原理和深入理解编程语言的语法结构具有重要意义。
6. 参考资料
- 《编译原理与技术》
- 课程实验文档及代码。
编译原理语法分析实验报告
编译原理语法分析实验报告编译原理实验报告一、实验目的本实验的主要目的是熟悉编译原理中的语法分析算法及相关知识,并通过实际编码实现一个简单的语法分析器。
二、实验内容1.完成一个简单的编程语言的语法定义,并用BNF范式表示;2.基于给定的语法定义,实现自顶向下的递归下降语法分析器;3.实验所用语法应包含终结符、非终结符、产生式及预测分析表等基本要素;4.实现语法分析器的过程中,需要考虑文法的二义性和优先级等问题。
三、实验步骤1.设计一个简单的编程语言的语法,用BNF范式进行表达。
例如,可以定义表达式文法为:<exp> ::= <term> { + <term> , - <term> }<term> ::= <factor> { * <factor> , / <factor> }<factor> ::= <digit> , (<exp>) , <variable><digit> ::= 0,1,2,3,4,5,6,7,8,9<variable> ::= a,b,c,...,z2. 根据所设计的语法,构建语法分析器。
首先定义需要用到的终结符、非终结符和产生式。
例如,终结符可以是+、-、*、/、(、)等,非终结符可以是<exp>、<term>、<factor>等,产生式可以是<exp> ::= <term> + <term> , <term> - <term>等。
3.实现递归下降语法分析器。
根据语法的产生式,编写相应的递归函数进行递归下降分析。
递归函数的输入参数通常是一个输入字符串和当前输入位置,输出结果通常是一个语法树或语法分析错误信息。
4.在语法分析的过程中,需要处理语法的二义性和优先级问题。
编译原理词法分析器语法分析器实验报告
printf("请输入各终结符(#号表示结束)Vt[i]:\n");
for(i=0;i<100;i++)
{
scanf("%c",&Vt[i]);
if(Vt[i]=='#')
{
r=i;
break;
}
}
printf("请输入非终结符个数:\n");
scanf("%d",&n);
getchar();
p=s->next;
while(p!=NULL)
{
st[i++]=p->data;
p=p->next;
}
for(j=i-1;j>=0;j--)
printf("%c",st[j]);
for(j=0;j<16-i;j++) //打印对齐格式
printf("%c",' ');
}
char gettop(stackk *s) //返回栈顶元素值
{
stackk *p;
p=(stackk *)malloc(sizeof(stackk));
p->data=x;
p->next=s->next;
s->next=p;
}
void display(stackk *s) //打印现实显示栈内元素
{
stackk *p;
int i=0,j;
char st[100];
#include<string.h>
#include<malloc.h>
编译原理语法分析器实验报告
西安邮电大学编译原理实验报告学院名称:计算机学院****:***实验名称:语法分析器的设计与实现班级:计科1405班学号:04141152时间:2017年5月12日一.实验目的1.熟悉语法分析的过程2.理解相关文法分析的步骤3.熟悉First集和Follow集的生成二.实验要求对于给定的文法,试编写调试一个语法分析程序:要求和提示:1)可选择一种你感兴趣的语法分析方法(LL(1)、算符优先、递归下降、SLR(1)等)作为编制语法分析程序的依据。
2)对于所选定的分析方法,如有需要,应选择一种合适的数据结构,以构造所给文法的机内表示。
3)能进行分析过程模拟。
如输入一个句子,能输出与句子对应的语法树,能对语法树生成过程进行模拟;能够输出分析过程每一步符号栈的变化情况。
设计一个由给定文法生成First集和Follow集并进行简化的算法动态模拟三.实验内容1.文法:E->TE’E’->+TE’|εT->FT’T’->*FT’|εF->(E)|i:2.程序描述(LL(1)文法)本程序是基于已构建好的某一个语法的预测分析表来对用户的输入字符串进行分析,判断输入的字符串是否属于该文法的句子。
基本实现思想:接收用户输入的字符串(字符串以“#”表示结束)后,对用做分析栈的一维数组和存放分析表的二维数组进行初始化。
然后取出分析栈的栈顶字符,判断是否为终结符,若为终结符则判断是否为“#”且与当前输入符号一样,若是则语法分析结束,输入的字符串为文法的一个句子,否则出错若不为“#”且与当前输入符号一样则将栈顶符号出栈,当前输入符号从输入字符串中除去,进入下一个字符的分析。
若不为“#”且不与当前输入符号一样,则出错。
3.判断是否LL(1)文法要判断是否为LL(1)文法,需要输入的文法G有如下要求:具有相同左部的规则的SELECT集两两不相交,即:SELECT(A→?)∩SELECT(A→?)= ?如果输入的文法都符合以上的要求,则该文法可以用LL(1)方法分析。
编译原理实验—语法分析器课件
学习交流PPT
2
测试文法:
① S ABBA Aa|ε Bb|ε
③ E E+T | T T T*F | F F (E) | i
② S aSe | B B bBe | C C cCe | d
④ S Qc | c Q Rb | b R Sa | a
学习交流PPT
3
二、算符优先分析法基本要求: 1) 任意输入一个文法G; 2) 判断该文法是否为算符文法; 3) 对文法中的每个非终结符自动生成并打印输出: ① FIRSTVT集; ② LASTVT集; 4)判断该文法是否为算符优先文法, 如果是自动生成并打印输出其算符优先矩阵; 5) 模拟分析过程。 如输入一个句子,如果该句子合法则输出与句子 对应的语法树;能够输出分析过程中每一步符号 栈的变化情况以及根据当前最左素短语进行归约 的过程。如果该句子非法则进行相应的报错处理。
学习交流PPT
4
测试文法:
① E TE’ E’ +TE’|ε T FT’ T’ *FT’|ε F (E)|i
② E E+T | T T T*F | F F P^F| P P(E)|i
学习交流PPT
5
实习报告内容:
1.实验目的 2.实验要求 3.实验内容 4.采用的数据结构 5.算法描述 6.运行结果 7.调试情况 8.设计技巧及体会 9.源程序清单(电子版)
实验—语法分析
学习交流PPT
1
பைடு நூலகம்
一、预测分析法基本要求: 1) 任意输入一个文法G; 2) 处理文法中可能存在的左递归和公共左因子问题; 3) 对文法中的每个非终结符自动生成并打印输出: ① FIRST集; ② FOLLOW集; 4)判断处理后的文法是否为LL(1)文法, 如果是,自动生成并打印输出其预测分析表; 5) 模拟分析过程。 如输入一个句子,如果该句子合法则输出与句子 对应的语法树;能够输出分析过程中每一步符号 栈的变化情况。如果该句子非法则进行相应的报 错处理。
编译原理实验报告(语法分析器)
.编译原理实验专业:13级网络工程语法分析器1一、实现方法描述所给文法为G【E】;E->TE’E’->+TE’|空T->FT’T’->*FT’|空F->i|(E)递归子程序法:首先计算出五个非终结符的first集合follow集,然后根据五个产生式定义了五个函数。
定义字符数组vocabulary来存储输入的句子,字符指针ch指向vocabulary。
从非终结符E函数出发,如果首字符属于E的first集,则依次进入T函数和E’函数,开始递归调用。
在每个函数中,都要判断指针所指字符是否属于该非终结符的first集,属于则根据产生式进入下一个函数进行调用,若first集中有空字符,还要判断是否属于该非终结符的follow集。
以分号作为结束符。
二、实现代码头文件shiyan3.h#include<iostream>#include<cstdio>#include<string>using namespace std;#define num 100char vocabulary[num];char *ch;void judge_E();void judge_EE();void judge_T();void judge_TT();void judge_F();源文件#include"shiyan3.h"void judge_E(){if(*ch==';'){cout<<"该句子符合此文法!"<<endl;int a=0;cout<<"按1结束程序"<<endl;cin>>a;if(a==1)exit(0);}elseif(*ch=='('||*ch=='i'){judge_T();judge_EE();}else{cout<<"该句子不匹配此文法!"<<endl;int a=0;cout<<"按1结束程序"<<endl;cin>>a;if(a==1)exit(0);}}void judge_EE(){if(*ch==';'){cout<<"该句子符合此文法!"<<endl;int a=0;cout<<"按1结束程序"<<endl;cin>>a;if(a==1)exit(0);}if(*ch=='+'){ch++;judge_T();judge_EE();}elseif(*ch=='#'||*ch==')')return;else{cout<<"该句子不匹配此文法!"<<endl;int a=0;cout<<"按1结束程序"<<endl;cin>>a;if(a==1)exit(0);}}void judge_T(){if(*ch==';'){cout<<"该句子符合此文法!"<<endl;int a=0;cout<<"按1结束程序"<<endl;cin>>a;if(a==1)exit(0);}if(*ch=='('||*ch=='i'){judge_F();judge_TT();}else{cout<<"该句子不匹配此文法!"<<endl;int a=0;cout<<"按1结束程序"<<endl;cin>>a;if(a==1)exit(0);}}void judge_TT(){if(*ch==';'){cout<<"该句子符合此文法!"<<endl;int a=0;cout<<"按1结束程序"<<endl;cin>>a;if(a==1)exit(0);}if(*ch=='*'){ch++;judge_F();judge_TT();}elseif(*ch==')'||*ch=='+'||*ch=='#')return;else{cout<<"该句子不匹配此文法!"<<endl;int a=0;cout<<"按1结束程序"<<endl;cin>>a;if(a==1)exit(0);}}void judge_F(){if(*ch==';'){cout<<"该句子符合此文法!"<<endl;int a=0;cout<<"按1结束程序"<<endl;cin>>a;if(a==1)exit(0);}if(*ch=='('){ch++;judge_E();if(*ch==')'){ch++;}else{cout<<"该句子不匹配此文法!"<<endl;int a=0;cout<<"按1结束程序"<<endl;cin>>a;if(a==1)exit(0);}}elseif(*ch=='i'){ch++;//cout<<*ch;}else{cout<<"该句子不匹配此文法!"<<endl;int a=0;cout<<"按1结束程序"<<endl;cin>>a;if(a==1)exit(0);}}void main(){//char *ch;cout<<"**********************欢迎使用语法分析器************************"<<endl;cout<<"请输入一个句子:"<<endl;cin.getline(vocabulary,15);ch=vocabulary;judge_E();cout<<endl;cout<<"************************结束使用,再见!**************************"<<endl;}三、运行结果四、心得体会此次实验使用的是递归子程序法,用这个方法最大的问题就是函数里的递归调用,一不小心就把人绕糊涂了。
编译原理_语法分析器
编译原理实验报告语法分析器一.实验目的及内容实验目的:编制一个语法分析程序,实现对词法分析程序所提供的单词序列进行语法检查和结构分析。
实验内容:在上机(一)词法分析的基础上,采用递归子程序法或其他适合的语法分析方法,实现其语法分析程序。
要求编译后能检查出语法错误。
已知待分析的C语言子集的语法,用EBNF表示如下:<程序>→main()<语句块><语句块> →‘{’<语句串>‘}’<语句串> → <语句> {; <语句> };<语句> → <赋值语句> |<条件语句>|<循环语句><赋值语句>→ID=<表达式><条件语句>→if‘(‘条件’)’<语句块><循环语句>→while’(‘<条件>’)‘<语句块><条件> → <表达式><关系运算符> <表达式><表达式> →<项>{+<项>|-<项>}<项> → <因子> {* <因子> |/ <因子>}<因子> →ID|NUM| ‘(’<表达式>‘)’<关系运算符> →<|<=|>|>=|==|!=二、实验原理及基本技术路线图(方框原理图或程序流程图)三、所用仪器、材料(设备名称、型号、规格等或使用软件)1台PC以及VISUAL C++6.0软件四、实验方法、步骤(或:程序代码或操作过程)#include <iostream>#include <string>using namespace std;char prog[80],token[8];char ch;int syn,p,m,n,sum,k=0;char *key[6]={"main","int","char","if","else","while"};void scaner();void lrparser();void yucu();void statement();void expression();void term();void factor();void main(){p=0;cout<<"语法分析"<<endl;cout<<"请输入字符串,以“@”结尾:"<<endl;do {ch = getchar(); prog[p++]=ch;}while(ch!='@');p=0;scaner();lrparser();}void scaner(){sum=m=0;for(n=0;n<8;n++) token[n]=NULL;ch=prog[p++];while(ch==' ') ch=prog[p++];if((ch>='a'&&ch<='z')||(ch>='A'&&ch<='Z')){while((ch>='a'&&ch<='z')||(ch>='A'&&ch<='Z')||(ch>='0'&&ch<='9')) {token[m++]=ch; ch=prog[p++];}token[m++]='\0';p--;syn=10;for(n=0;n<6;n++)if(strcmp(token,key[n])==0){syn=n+1; break;}}else if(ch>='0'&&ch<='9'){while(ch>='0'&&ch<='9'){sum=sum*10+ch-'0';ch=prog[p++];}p--;syn=20;}elseswitch(ch){case '<': m=0;token[m++]=ch;ch=prog[p++];if(ch=='<') {syn=33; token[m++]=ch;}else if(ch=='=') {syn=35; token[m++]=ch;}break;case '>': m=0;token[m++]=ch;ch=prog[p++];if(ch=='=') {syn=34; token[m++]=ch;}else {syn=32; p--;}break;case '=':token[m++]=ch;ch=prog[p++];if(ch=='='){ syn=36;token[m++]=ch;}else{ syn=21;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=22; token[0]=ch; break;case '-': syn=23; token[0]=ch; break;case '*': syn=24; token[0]=ch; break;case '/': syn=25; token[0]=ch; break;case ';': syn=31; token[0]=ch; break;case '(': syn=26; token[0]=ch; break;case ')': syn=27; token[0]=ch; break;case '@': syn=0; token[0]=ch; break;default : syn=-1;}}void lrparser(){if(syn==1){scaner();yucu();if(syn=6){scaner();if(syn==0 && (k==0))cout<<"\nsuccess\n"<<endl;}else{if(k!=1)cout<<"\nwhile error\n"<<endl;k=1;}}else{cout<<"\nmain error\n"<<endl;k=1;}return;}void yucu(){statement();while(syn==31){scaner();statement();}return;}void statement(){if(syn==10){scaner();if(syn==18){scaner();expression();}else{cout<<"\nscentence error\n"<<endl;k=1;}}return;}void expression(){term();while(syn==22||syn==23){scaner();term();}return;}void term(){factor();while(syn==24||syn==25){scaner();factor();}return;}void factor(){if(syn==10||syn==20)scaner();else if(syn==26){scaner();expression();if(syn==27)scaner();else{cout<<"( error"<<endl;k=1;}}else{cout<<"expression error"<<endl;k=1;}return;}五、实验过程原始记录( 测试数据、图表、计算等)六、实验结果、分析和结论(误差分析与数据处理、成果总结等。
编译原理实验报告——实验三 语法分析分析器
//判断文法是否合法
if(st[i][j]>='A'&&st[i][j]<='Z') { if(st[i][j+1]>='A'&&st[i][j+1]<='Z') { printf("不是算符文法!\n"); exit(-1); } } } } for(i=0;i<r;i++) { for(j=0;st[i][j]!='\0';j++) { if((st[i][j]<'A'||st[i][j]>'Z')&&st[i][j]!='-'&&st[i][j]!='>'&&st[i][j]!='|') lable[k++]=st[i][j]; } } lable[k]='#'; lable[k+1]='\0'; table();
return六实验者自评主要从实验态度方法效果上给一个客观公正的自我评价这次实验编写了两个词法分析方法的程序但是在ll1分析器的编写中我只达到了最低要求就是自己手动输入的select集first集follow集然后通过程序将预测分析表构造出来了并且没有做出对输入串的分析
编译原理实验报告
实验名称: 实验类型: 指导教师: 专业班级: 姓 学 名: 号:
first[i][0]=0;
ቤተ መጻሕፍቲ ባይዱ
/*first[i][0]和 last[i][0]分别表示 st[i][0]非终极
编译原理-语法分析器-仅供参考,不可滥用!
青岛理工大学课程实验报告
(2).递归下降分析程序示意图(左)语法串分析程序示意图(右)
(4)statement 语法分析程序流程图(左)expression表达式分析函数示意图(右)
(3)term分析函数示意图(左)factor分析过程示意图(右)
调试过程及实验1.测试一
输入begin x:=9; x:=2*3; b:=a+x;end ;# 后经语法分析输出如图所示:
结
果
2.测试二
输入x:=a+b*c end # 后经语法分析输出如图所示:
3.测试三
输入 begin q:=6; d:=4; end #,经语法分析输出如图所示:
4.测试四
输入 begin a:=4;b:=5;c:=a*b+a #,经语法分析输出如图所示:
总结
通过本次试验,我们设计出了一个比较符合要求的语法分析器,同时了解了语法分析的过程,其主程序大致流程为:“置初值”→调用wordScanAnalyse函数读下一个单词符号→调用IrParse→结束。
分析程序的各个判断条件可以知道,需要调用函数factor();expression();yucu();term();statement();lrparser();其中嵌套了条件语句
使得拥有较为全面的处理机制,当程序不以“begin”开头,或不以“end #”。
编译原理实验词法分析器与语法分析器实现
编译原理实验词法分析器与语法分析器实现词法分析器与语法分析器是编译器的两个重要组成部分,它们在编译过程中扮演着至关重要的角色。
词法分析器负责将源代码转化为一个个标记(token)序列,而语法分析器则根据词法分析器生成的标记序列构建语法树,验证源代码的语法正确性。
本实验旨在实现一个简单的词法分析器和语法分析器。
实验一:词法分析器实现在实现词法分析器之前,需要定义所需词法项的规则。
以C语言为例,常见的词法项包括关键字(如int、if、for等)、标识符、运算符(如+、-、*、/等)、常量(如整数、浮点数等)和分隔符(如括号、逗号等)。
接下来,我们来实现一个简单的C语言词法分析器。
1. 定义词法项的规则在C语言中,关键字和标识符由字母、数字和下划线组成,且首字符不能为数字。
运算符包括各种数学运算符和逻辑运算符。
常量包括整数和浮点数。
分隔符包括括号、逗号等。
2. 实现词法分析器的代码下面是一个简单的C语言词法分析器的实现代码:```pythondef lexer(source_code):keywords = ['int', 'if', 'for'] # 关键字列表operators = ['+', '-', '*', '/'] # 运算符列表separators = ['(', ')', '{', '}', ',', ';'] # 分隔符列表tokens = [] # 标记序列列表current_token = '' # 当前标记for char in source_code:if char.isspace(): # 如果是空格,则忽略continueelif char.isalpha(): # 如果是字母,则可能是关键字或标识符的一部分current_token += charelif char.isdigit(): # 如果是数字,则可能是常量的一部分current_token += charelif char in operators or char in separators: # 如果是运算符或分隔符,则当前标记结束if current_token:tokens.append(current_token)current_token = ''tokens.append(char)else: # 如果是其他字符,则当前标记结束if current_token:tokens.append(current_token)current_token = ''return tokens```以上代码通过遍历源代码的字符,根据定义的规则生成一个个标记,存储在`tokens`列表中。
编译原理实验——语法分析器报告
组员学号姓名实验名称对各算术表达式进行语法分析实验室实验目的或要求实验目的:1、掌握语法分析器生成工具的使用和了解编译器的设计;2、了解自上而下语法分析器的构造过程;3、能够构造LR分析表,编写由该分析表驱动的语法分析器程序;4、借助语法制导翻译,可在语法分析的同时,完成对语义的翻译;5、借助语法分析,设计一个表达式的判断分析器,即从键盘上输入算术表达式,分析器将显示该表达式的正确与否。
实验原理(算法流程)实验算法流程图如下所示:开始输入表达式表达式保存到数ch第一个元素为)+-*/YCh[i]=’(’i++YNCh[i]=NULLNCh[i]是0~9i++YCh[i]是0~9Ch[i]=+ -*/)N多了+ -*/)Y其他错误NYCh[i]=* /Ni++YCh[i]=+ -*/NY多了+ -*/Ch[i]=+ -NNCh[i]=)Y少了)N错误首部多了) +-*/结束程序界面(效果图)实验结果界面:只选择几个典型的例子进行分析,可进行任意表达式输入。
1)未进行语法分析时的界面;2)输入正确的表达式(1+2)*(6-3)+1进行语法分析时的界面结果;3)输入错误的表达式1*2+(2+3并进行语法分析时的界面结果;程序界面(效果图)4)输入错误的表达式1+(+5+6)并进行语法分析时的界面结果;程序界面(效果图)程序代码 #include "stdafx.h"#include "grammer.h"#include "mfc_语法分析器.h"#include "mfc_语法分析器Dlg.h"int flag;int i,j;int length;CString string;int grammer(CString str){i=0;flag=0;char ch[MAX];length=str.GetLength();strcpy(ch,str);if(length!=0){F(ch);if(flag==0){MessageBox(NULL,"输入表达式符合文法","正确",MB_OK|MB_ICONINFORMATION);}//str=ch;//return flag;}else{MessageBox(NULL,"表达式为空","提示",MB_OK|MB_ICONW ARNING);//MessageBox(NULL,"表达式为空","提示",MB_OK|MB_ICONERROR);return -1;}return flag;}void F(char ch[]){if(ch[0]=='+'){程序代码flag=0;MessageBox(NULL,"输入表达式不符合文法0","错误",MB_OK|MB_ICONERROR); MessageBox(NULL,"开始处多了+","提示",MB_OK|MB_ICONINFORMA TION);flag=1;}elseif(ch[0]=='-'){flag=0;MessageBox(NULL,"输入表达式不符合文法0","错误",MB_OK|MB_ICONERROR);MessageBox(NULL,"开始处多了-","提示",MB_OK|MB_ICONINFORMA TION);flag=1;}elseif(ch[0]=='*'){flag=0;MessageBox(NULL,"输入表达式不符合文法0","错误",MB_OK|MB_ICONERROR);MessageBox(NULL,"开始处多了*","提示",MB_OK|MB_ICONINFORMA TION);flag=1;}elseif(ch[0]=='/'){flag=0;MessageBox(NULL,"输入表达式不符合文法0","错误",MB_OK|MB_ICONERROR);MessageBox(NULL,"开始处多了/","提示",MB_OK|MB_ICONINFORMA TION);flag=1;}elseif(ch[0]==')'){flag=0;MessageBox(NULL,"输入表达式不符合文法0","错误",MB_OK|MB_ICONERROR);MessageBox(NULL,"开始处多了)","提示",MB_OK|MB_ICONINFORMA TION);flag=1;}/*上述为对第一个字符的特殊处理*/elseif(ch[i]!=NULL){if(ch[i]=='('){i++;F(ch);程序代码if(ch[i]!=')'){if(flag==0){MessageBox(NULL,"输入表达式不符合文法1","错误",MB_OK|MB_ICONERROR);MessageBox(NULL,"少了')'","提示",MB_OK|MB_ICONINFORMATION);}flag=1;}else{i++;if(ch[i]!=NULL)T(ch);}}elseif(ch[i]<='9'&&ch[i]>='0'){while(ch[i]<='9'&&ch[i]>='0')i++;if(ch[i]!=NULL)T(ch);}else{if(flag==0){if(ch[i]!=NULL&&ch[i]!=')'){MessageBox(NULL,"输入表达式不符合文法2.1","错误",MB_OK|MB_ICONERROR);if(ch[i]==' ') MessageBox(NULL,"含有空格","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i]=='+') {MessageBox(NULL,"多了'+'号","提示",MB_OK|MB_ICONINFORMA TION);}else if(ch[i]=='-') MessageBox(NULL,"多了'-'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i]=='*') MessageBox(NULL,"多了'*'号","提示",MB_OK|MB_ICONINFORMA TION);程序代码else if(ch[i]=='/') MessageBox(NULL,"多了'/'号","提示",MB_OK|MB_ICONINFORMA TION);}else if(ch[i]==NULL){MessageBox(NULL,"输入表达式不符合文法2.2","错误",MB_OK|MB_ICONERROR);if(ch[i-1]==' ') MessageBox(NULL,"含有空格","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i-1]=='+') MessageBox(NULL,"多了最后的'+'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i-1]=='-') MessageBox(NULL,"多了最后的'-'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i-1]=='*') MessageBox(NULL,"多了最后的'*'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i-1]=='/') MessageBox(NULL,"多了最后的'/'号","提示",MB_OK|MB_ICONINFORMA TION);}else if(ch[i]!=NULL&&ch[i]==')'){MessageBox(NULL,"输入表达式不符合文法2.3","错误",MB_OK|MB_ICONERROR);if(ch[i-1]==' ') MessageBox(NULL,"含有空格","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i-1]=='(') MessageBox(NULL,"含有一对空括号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i-1]=='+') MessageBox(NULL,"多了最后的'+'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i-1]=='-') MessageBox(NULL,"多了最后的'-'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i-1]=='*') MessageBox(NULL,"多了最后的'*'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i-1]=='/') MessageBox(NULL,"多了最后的'/'号","提示",MB_OK|MB_ICONINFORMA TION);}}flag=1;}}}void T(char ch[]){if(ch[i]=='*'||ch[i]=='/')程序代码{i++;if(ch[i]!=NULL&&ch[i]!='+'&&ch[i]!='-'&&ch[i]!='*'&&ch[i]!='/')F(ch);else{if(flag==0){MessageBox(NULL,"输入表达式不符合文法3","错误",MB_OK|MB_ICONERROR);if(ch[i]==' ') MessageBox(NULL,"含有空格","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i]=='+') MessageBox(NULL,"多了'+'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i]=='-') MessageBox(NULL,"多了'-'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i]=='*') MessageBox(NULL,"多了'*'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i]=='/') MessageBox(NULL,"多了'/'号","提示",MB_OK|MB_ICONINFORMA TION);}flag=1;}}elseE(ch);}void E(char ch[]){if(ch[i]=='+'||ch[i]=='-'){i++;if(ch[i]!=NULL&&ch[i]!='+'&&ch[i]!='-'&&ch[i]!='*'&&ch[i]!='/')F(ch);else{if(flag==0){if(ch[i]!=NULL){MessageBox(NULL,"输入表达式不符合文法4.1","错误",MB_OK|MB_ICONERROR);if(ch[i]==' ') MessageBox(NULL,"含有空格","提示",MB_OK|MB_ICONINFORMA TION);程序代码else if(ch[i]=='+') MessageBox(NULL,"多了'+'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i]=='-') MessageBox(NULL,"多了'-'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i]=='*') MessageBox(NULL,"多了'*'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i]=='/') MessageBox(NULL,"多了'/'号","提示",MB_OK|MB_ICONINFORMA TION);}else if(ch[i]==NULL){MessageBox(NULL,"输入表达式不符合文法4.2","错误",MB_OK|MB_ICONERROR);if(ch[i-1]==' ') MessageBox(NULL,"含有空格","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i-1]=='+') MessageBox(NULL,"多了最后的'+'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i-1]=='-') MessageBox(NULL,"多了最后的'-'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i-1]=='*') MessageBox(NULL,"多了最后的'*'号","提示",MB_OK|MB_ICONINFORMA TION);else if(ch[i-1]=='/') MessageBox(NULL,"多了最后的'/'号","提示",MB_OK|MB_ICONINFORMA TION);}}flag=1;}}else if(ch[i]!=')'){if(flag==0){MessageBox(NULL,"输入表达式不符合文法5","错误",MB_OK|MB_ICONERROR);if(ch[i]=='('&&ch[i+2]==')') MessageBox(NULL,"含有一对多余的括号","提示",MB_OK|MB_ICONINFORMA TION);else MessageBox(NULL,"其他类型的错误","提示",MB_OK|MB_ICONINFORMA TION);}flag=1;}}实验结果分析及心得体会实验结果分析:本次实验借助语法分析,设计一个表达式的判断分析器,从键盘上输入算术表达式,分析器对该表达式的正确与否进行分析。
编译原理语法分析器
编译原理语法分析器编译原理语法分析器是编译器中的重要组成部分,它负责将源代码解析成抽象语法树,为后续的语义分析和代码生成做准备。
本文将介绍语法分析器的原理、分类和常用算法。
一、语法分析器的原理语法分析器的主要任务是根据给定的文法定义,将源代码解析成一个个语法单元,并构建出一棵抽象语法树。
它通过递归下降、预测分析和LR分析等算法来实现。
1. 递归下降法递归下降法是一种基于产生式的自顶向下分析方法。
它从文法的开始符号出发,通过不断地推导和回溯,逐步地构建抽象语法树。
递归下降法易于理解和实现,但对左递归和回溯有一定的局限性。
2. 预测分析法预测分析法也是自顶向下的分析方法,它通过预测下一个输入符号来选择适当的产生式进行推导。
为了提高效率,预测分析法使用预测分析表来存储各个非终结符和终结符的关系。
3. LR分析法LR分析法是一种自底向上的分析方法,它使用LR自动机和LR分析表来进行分析。
LR自动机是一个有限状态控制器,通过状态转移和规约动作来解析源代码。
LR分析表存储了状态转移和规约的规则。
二、语法分析器的分类根据语法分析器的特性和实现方式,可以将其分为LL分析器和LR 分析器。
1. LL分析器LL分析器是基于递归下降法和预测分析法的一类分析器。
它从左到右、从左到右地扫描源代码,并根据预测分析表进行推导。
常见的LL分析器有LL(1)分析器和LL(k)分析器。
2. LR分析器LR分析器是基于LR分析法的一类分析器。
它先通过移进-归约的方式建立一棵语法树,然后再进行规约操作。
LR分析器具有强大的语法处理能力,常见的LR分析器有LR(0)、SLR(1)、LR(1)和LALR(1)分析器。
三、常用的语法分析算法除了递归下降法、预测分析法和LR分析法,还有一些其他的语法分析算法。
1. LL算法LL算法是一种递归下降法的改进算法,它通过构造LL表和预测分析表实现分析过程。
LL算法具有很好的可读性和易于理解的特点。
2. LR算法LR算法是一种自底向上的分析方法,它通过建立LR自动机和构造LR分析表来进行分析。
编译原理实验二:LL(1)语法分析器
编译原理实验⼆:LL(1)语法分析器⼀、实验要求 1. 提取左公因⼦或消除左递归(实现了消除左递归) 2. 递归求First集和Follow集 其它的只要按照课本上的步骤顺序写下来就好(但是代码量超多...),下⾯我贴出实验的⼀些关键代码和算法思想。
⼆、基于预测分析表法的语法分析 2.1 代码结构 2.1.1 Grammar类 功能:主要⽤来处理输⼊的⽂法,包括将⽂法中的终结符和⾮终结符分别存储,检测直接左递归和左公因⼦,消除直接左递归,获得所有⾮终结符的First集,Follow集以及产⽣式的Select集。
#ifndef GRAMMAR_H#define GRAMMAR_H#include <string>#include <cstring>#include <iostream>#include <vector>#include <set>#include <iomanip>#include <algorithm>using namespace std;const int maxn = 110;//产⽣式结构体struct EXP{char left; //左部string right; //右部};class Grammar{public:Grammar(); //构造函数bool isNotTer(char x); //判断是否是终结符int getTer(char x); //获取终结符下标int getNonTer(char x); //获取⾮终结符下标void getFirst(char x); //获取某个⾮终结符的First集void getFollow(char x); //获取某个⾮终结符的Follow集void getSelect(char x); //获取产⽣式的Select集void input(); //输⼊⽂法void scanExp(); //扫描输⼊的产⽣式,检测是否有左递归和左公因⼦void remove(); //消除左递归void solve(); //处理⽂法,获得所有First集,Follow集以及Select集void display(); //打印First集,Follow集,Select集void debug(); //⽤于debug的函数~Grammar(); //析构函数protected:int cnt; //产⽣式数⽬EXP exp[maxn]; //产⽣式集合set<char> First[maxn]; //First集set<char> Follow[maxn]; //Follow集set<char> Select[maxn]; //select集vector<char> ter_copy; //去掉$的终结符vector<char> ter; //终结符vector<char> not_ter; //⾮终结符};#endif 2.1.2 AnalyzTable类 功能:得到预测分析表,判断输⼊的⽂法是否是LL(1)⽂法,⽤预测分析表法判断输⼊的符号串是否符合刚才输⼊的⽂法,并打印出分析过程。
编译原理语法分析实验报告
编译原理语法分析实验报告一、实验目的本实验主要目的是学习和掌握编译原理中的语法分析方法,通过实验了解和实践LR(1)分析器的实现过程,并对比不同的文法对语法分析的影响。
二、实验内容1.实现一个LR(1)的语法分析器2.使用不同的文法进行语法分析3.对比不同文法对语法分析的影响三、实验原理1.背景知识LR(1)分析器是一种自底向上(bottom-up)的语法分析方法。
它使用一个分析栈(stack)和一个输入缓冲区(input buffer)来处理输入文本,并通过移进(shift)和规约(reduce)操作进行语法分析。
2.实验步骤1)构建文法的LR(1)分析表2)读取输入文本3)初始化分析栈和输入缓冲区4)根据分析表进行移进或规约操作,直至分析过程结束四、实验过程与结果1.实验环境本实验使用Python语言进行实现,使用了语法分析库ply来辅助实验。
2.实验步骤1)构建文法的LR(1)分析表通过给定的文法,根据LR(1)分析表的构造算法,构建出分析表。
2)实现LR(1)分析器使用Python语言实现LR(1)分析器,包括读取输入文本、初始化分析栈和输入缓冲区、根据分析表进行移进或规约操作等功能。
3)使用不同的文法进行语法分析选择不同的文法对编写的LR(1)分析器进行测试,观察语法分析的结果。
3.实验结果通过不同的测试案例,实验结果表明编写的LR(1)分析器能够正确地进行语法分析,能够识别出输入文本是否符合给定文法。
五、实验分析与总结1.实验分析本实验通过实现LR(1)分析器,对不同文法进行语法分析,通过实验结果可以观察到不同文法对语法分析的影响。
2.实验总结本实验主要学习和掌握了编译原理中的语法分析方法,了解了LR(1)分析器的实现过程,并通过实验提高了对语法分析的理解。
六、实验心得通过本次实验,我深入学习了编译原理中的语法分析方法,了解了LR(1)分析器的实现过程。
在实验过程中,我遇到了一些问题,但通过查阅资料和请教老师,最终解决了问题,并完成了实验。
编译原理实验报告-语法分析
编译原理课程实验报告实验2:语法分析Program—〉PP-〉DP|S P|emptyD—>proc Tid(M){ P }|T id A ;|record id{ P}M-〉X id M’M’->,XidM'|emptyA->=F|empty|,id AF->digit|id|char|{G}|stringG->H G’G'-〉, H G'|emptyH->digit|charT—>XCX-〉short|int|long|float|double|char|void|string|booleanC—>[ digit ]C|emptyS-〉L = E ;|if B thenS elseS|while Bdo S|call id(Elist );|return E ;E-〉—EE'|( E )E’|digit E'|L E’|string E’E'—>+E E’|* E E'|emptyL->idL'L'->[digit]L'|emptyB—>! B B'|( B ) B'|E relopE B'|true B’|falseB’B'->or B B'|andB B’|emptyrelop->〈|<=|==|!=|〉|>=Elist-〉E Elist’Elist'-〉,EElist’|empty注:此处用empty代表空三、系统设计得分要求:分为系统概要设计与系统详细设计。
(1)系统概要设计:给出必要得系统宏观层面设计图,如系统框架图、数据流图、功能模块结构图等以及相应得文字说明.1)系统得数据流图:说明说明:本语法分析器就是基于上一个实验词法分析器得基础上,通过在界面写或者就是导入源程序,词法分析器将源程序识别得词法单元传递给语法分析器,语法分析器验证这个词法单元组成得串就是否可以由源语言得文法生成,能够输出语法分析得结果,文法得first集、f ollow集与预测分析表,当然也可以以易于理解得方式报告语法错误。
语法分析器实验报告
语法分析器实验报告实验报告:语法分析器的设计与实现摘要:语法分析器是编译器的一个重要组成部分,主要负责将词法分析器输出的词法单元序列进行分析和解释,并生成语法分析树。
本实验旨在设计与实现一个基于上下文无关文法的语法分析器,并通过实现一个简单的编程语言的解释器来验证其功能。
1.引言在计算机科学中,编译器是将高级程序语言转化为机器语言的一种工具。
编译器通常由词法分析器、语法分析器、语义分析器、中间代码生成器、优化器和目标代码生成器等多个模块组成。
其中,语法分析器负责将词法分析器生成的词法单元序列进行进一步的分析与解释,生成语法分析树,为后续的语义分析和中间代码生成提供基础。
2.设计与实现2.1上下文无关文法上下文无关文法(CFG)是指一类形式化的语法规则,其中所有的产生式规则都具有相同的左部非终结符,且右部由终结符和非终结符组成。
语法分析器的设计与实现需要依据给定的上下文无关文法来进行,在本实验中,我们设计了一个简单的CFG,用于描述一个名为"SimpleLang"的编程语言。
2.2预测分析法预测分析法是一种常用的自顶向下的语法分析方法,它利用一个预测分析表来决定下一步的推导选择。
预测分析表的构造依赖于给定的上下文无关文法,以及文法的FIRST集和FOLLOW集。
在本实验中,我们使用了LL(1)的预测分析法来实现语法分析器。
2.3语法分析器实现在实现语法分析器的过程中,我们首先需要根据给定的CFG构造文法的FIRST集和FOLLOW集,以及预测分析表。
接下来,我们将词法分析器输出的词法单元序列作为输入,通过不断地匹配输入符号与预测分析表中的预测符号,进行语法分析和推导。
最终,根据CFG和推导过程,构建语法分析树。
3.实验结果与分析通过实验发现,自顶向下的预测分析法在对简单的编程语言进行语法分析时具有较高的效率和准确性。
语法分析器能够正确地识别输入程序中的语法错误,并生成相应的错误提示信息。
编译原理实验报告(词法分析器-语法分析器)
else if(strcmp(token,"if")==0) return(2);
else if(strcmp(token,"else")==0) return(3);
else if(strcmp(token,"switch")==0) return(4);
}
j=0;
get();
}}
六:实验结果:
实验二
一、实验名称:语法分析器的设计
二、实验目的:
用C语言编写对一个算术表达式实现语法分析的语法分析程序,并以四元式的形式输出,以加深对语法语义分析原理的理解,掌握语法分析程序的实现方法和技术。
三、 实验原理:
1、算术表达式语法分析程序的算法思想
首先通过关系图法构造出终结符间的左右优先函数f(a),g(a)。在分析的过程中,通过左右优先函数比较当前读入终结符和前一个读入终结符间的优先关系,分析后适时的以四元式形式输出相关的符号。
编
译
原
理
实
验
报
告
实验一
一、实验名称:词法分析器的设计
二、实验目的:1,词法分析器能够识别简单语言的单词符号
2,识别出并输出简单语言的基本字.标示符.无符号整数.运算符.和界符。
三、实验要求:给出一个简单语言单词符号的种别编码词法分析器
四、实验原理:
1、词法分析程序的算法思想
算法的基本任务是从字符串表示的源程序中识别出具有独立意义的单词符号,其基本思想是根据扫描到单词符号的第一个字符的种类,拼出相应的单词符号。
i=1;
j=0;
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
编译原理
实验—语法分析
二、算符优先分析法基本要求: 1) 任意输入一个文法G; 2) 判断该文法是否为算符文法; 3) 对文法中的每个非终结符自动生成并打印输出: ① FIRSTVT集; ② LASTVT集; 4)判断该文法是否为算符优先文法, 如果是自动生成并打印输出其算符优先矩阵; 5) 模拟分析过程。 如输入一个句子,如果该句子合法则输出与句子 对应的语法树;能够输出分析过程中每一步符号 栈的变化情况以及根据当前最左素短语进行归约 的过程。如果该句子非法则进行相应的报错处理。
编译原理
实验—语法分析
实验—语法分析
编译原理
实验—语法分析
一、预测分析法基本要求: 1) 任意输入一个文法G; 2) 处理文法中可能存在的左递归和公共左因子问题; 3) 对文法中的每个非终结符自动生成并打印输出: ① FIRST集; ② FOLLOW集; 4)判断处理后的文法是否为LL(1)文法, 如果是,自动生成并打印输出其预测分析表; 5) 模拟分析过程。 如输入一个句子,如果该句子合法则输出与句子 对应的语法树;能够输出分析过程中每一步符号 栈的变化情况。如果该句子非法则进行相应的报 错处理。
编译原理
实验—语法分析
测试文法: ① E TE’ E’ +TE’|ε T FT’ T’ *FT’|ε F (E)|i ② E E+T | T T T*F | F F P^F| P P(E)|i
编译原理
实验—语法分析
实习报告内容: 1.实验目的 2.实验要求 3.实验内容 4.采用的数据结构 5.算法描述 6.运行结果 7.调试情况 8.设计技巧及体会 9.源程序清单(电子版)
ቤተ መጻሕፍቲ ባይዱ
编译原理
实验—语法分析
测试文法: ① S ABBA Aa|ε Bb|ε ③ E E+T | T T T*F | F F (E) | i ② S aSe | B B bBe | C C cCe | d ④ S Qc | c Q Rb | b R Sa | a