基于C++设计与实现的算符优先分析器

一、实验目的及要求

1.1 目的

加深对语法分析器工作过程的理解;加强对算符优先分析法实现语法分析程序的掌握;能够采用一种编程语言实现简单的语法分析程序;能够使用自己编写的分析程序对简单的程序段进行语法翻译。

1.2 要求

对语法规则有明确的定义
编写的分析程序能够对实验一的结果进行正确的语法分析
对于遇到的语法错误,能够做出简单的错误处理,给出简单的错误提示,保证顺利完成语法分析过程
软件、硬件环境:code::blocks 10.05,win10系统

二、实验步骤

2.1 实验步骤

定义目标语言的语法规则
求解预测分析方法需要的符号集和分析表
输入将要进行分析的句子
根据预测分析的方法进行语法分析,直到源程序结束
对遇到的语法错误做出错误处理

2.2 文法定义

E->E*T
F->T
T->(E)
T->i

2.3 求出FIRSTVT和LASTVT

FIRSTVT	LASTVT
E	*  (   i	*   )   i
T	(   i	)   i

2.4 画出算符优先分析表

*	(	)	i	#
*	>	<	>	<	>
(	<	<	=	<	>
)	>		>		
i	>		>		>
# 	<	<		<	=

三、实验内容

# include<stdlib.h>
# include<stdio.h>
# include<string.h>
# include<iostream>
# define SIZE 128
char priority[6][6]={{0},{'>','>','<','<','>','>'},{'>','>','$','$','>','>'},{'<','<','<','<','=','$'},
{'>','>','$','$','>','>'},{'<','<','<','<','$','='}};
char input[SIZE];     
char remain[SIZE];    
char AnalyseStack[SIZE];  
int  testchar(char x),k;  
void remainString();    
int testchar(char x){
    int m;
    if(x=='+')  m=0;
    if(x=='*')  m=1;
    if(x=='i')  m=2;
    if(x=='(')  m=3;
    if(x==')')  m=4;
    if(x=='#')  m=5;
    return m;
}
void analyse(){
    int i,j,f,z,z1,n,n1,z2,n2;
    int count=0;
    char a;
    char p,Q,p1,p2;
    f=strlen(input);  
    for(i=0;i<=f;i++) {
        a=input[i];
        if(i==0)  remainString();
        if(AnalyseStack[k]=='+'||AnalyseStack[k]=='*'||AnalyseStack[k]=='i'
     ||AnalyseStack[k]=='('||AnalyseStack[k]==')'||AnalyseStack[k]=='#')
            j=k;
        else  j=k-1;
        z=testchar(AnalyseStack[j]);
        if(a=='+'||a=='*'||a=='i'||a=='('||a==')'||a=='#')  n=testchar(a);
        else //如果句子含有不是终结符集合里的其它字符,不合法
            printf("错误!该句子不是该文法的合法句子!\n");  break;
        p=priority[z][n];
        if(p=='$'){
            printf("错误!该句子不是该文法的合法句子!\n");  return;
        }
        if(p=='>'){
 for( ; ; ){
               Q=AnalyseStack[j];
             if(AnalyseStack[j-1]=='+'||AnalyseStack[j-1]=='*'||AnalyseStack[j-1]=='i'
       ||AnalyseStack[j-1]=='('||AnalyseStack[j-1]==')'||AnalyseStack[j-1]=='#')
                 j=j-1;
             else  j=j-2;
             z1=testchar(AnalyseStack[j]);
             n1=testchar(Q);
             p1=priority[z1][n1];
             if(p1=='<') {
                 count++;
                 printf("(%d)     %s\t%10c\t%5c%17s\t    归约\n",count,AnalyseStack,p,a,remain);
                 k=j+1;  i--;
                 AnalyseStack[k]='N';  int r,r1;
                 r=strlen(AnalyseStack);
                 for(r1=k+1;r1<r;r1++)
                     AnalyseStack[r1]='\0';
             break;
             }
             else  continue;
        }
    }
        else{
            if(p=='<'){ 
                count++;
                printf("(%d)     %s\t%10c\t%5c%17s\t    移进\n",count,AnalyseStack,p,a,remain);
                k=k+1;
                AnalyseStack[k]=a;
                remainString();
            }
            else{
                if(p=='='){
                    z2=testchar(AnalyseStack[j]);
                    n2=testchar('#');  p2=priority[z2][n2];
                    if(p2=='='){
                        count++;
                        printf("(%d)     %s\t%10c\t%5c%17s\t    接受\n",count,AnalyseStack,p,a,remain);
                        printf("该句子是该文法的合法句子。\n");
                        break;
                    }
                    else{
                        count++;
                        printf("(%d)     %s\t%10c\t%5c%17s\t    移进\n",count,AnalyseStack,p,a,remain);
                        k=k+1;
                        AnalyseStack[k]=a;  remainString();
                    }
                }
                else
                    printf("错误!该句子不是该文法的合法句子!\n");  break;
            }
        }
    }
}
void remainString(){
    int i,j;  i=strlen(remain);
    for(j=0;j<i;j++)  remain[j]=remain[j+1];
    remain[i-1]='\0';
}
int main(){
    printf("请输入要进行分析的句子(以#号结束输入):\n");
    gets(input);  k=0;
    printf("步骤    栈           优先关系    当前符号    剩余输入串   移进或归约\n");
    AnalyseStack[k]='#';  AnalyseStack[k+1]='\0';
    int length,i;   length=strlen(input);
    for(i=0;i<length;i++)  remain[i]=input[i];
    remain[i]='\0';  analyse();
    return 0;
}

四、实验结果

4.1 运行截图

4.png

五、实验总结

本次实验基本完成了实验题目的要求,定义了一个文法,求出了每一个非终结符的VT集和LASTVT集,画出了算符优先关系表,并判定出给定的文法是否是算符优先文法。当给定一个 句子时,能够判定是否是文法中的句子,并能够将分析过程打印出来。
这个实验最大的收获,不仅仅使我更进一步的了解到了算符优先算法是一个省略了所有单非终结符产生式对应的归约步骤,其分析效率是很高的,同时,通过此次实验让我的处理问题的能力,思考问题的角度都得到了很大的提高,从词法分析到语法分析再到语义分析,基本走完了编译器的大致流程,这对我理解编译的过程和具体的实现都是有极大的帮助的。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

神仙别闹

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值