📄 源代码.cpp
字号:
#include<iostream>
#include <iomanip>
using namespace std;
int q=1;//控制分析栈的栈顶,定义为全局变量
int i=0;//控制输入待分析的字符
int x;//记录查询到的非终结符的数字代码
int y;//记录查询到的终结符的数字代码
void print(int m);//声明函数
//存储待分析的句子
char sentence[20];
//构建预测分析表,元素为规则的数字代码
int pat[4][7]={//predict analytical table(预测分析表的缩写)
{0,0,0,0,0,0,0},//为了使下标从1开始,多添了一行,一列(数组下标从0开始)
{0,1,2,3,0,0,0},//0 代表无规则
{0,4,4,4,0,0,0},//1:S-a; 2:S-b 3:S-(T) 4:T-SU 5:U-,SU 6:U-ε
{0,0,0,0,6,5,0}
};
//分析栈
char as[20]={'#','S'};//analysis stack
//文法规则
struct rules{
int n;//记录规则的字符数
char rule[5];//规则
}ruletable[7]={
{0,'$'},//无用,占位
{1,'a'},
{1,'b'},
{3,"(T)"},
{2,"SU"},
{3,",SU"},
{1,'$'}//$代表 ε
};
//根据规则填写分析栈
void fill(int p){
int w;//控制填表次数
int j=ruletable[p].n;//记录规则中,字符的个数
int m=j;
if(ruletable[p].rule[j-1]!='$'){//不是空规则
for(w=0;w<m;w++){//由规则中字符的个数决定填表的次数
as[q]=ruletable[p].rule[j-1];//倒序写入
q++;//准备填写分析栈下一个
j--;//填写下一个规则字符
}
q--;//每次填写完毕,q++,最后一次也是,应修正,以指示栈顶
print(i);//打印分析栈
}
else{
q--;//空规则,不写入分析栈,但栈顶需要回缩一个字符
print(i);//打印分析栈
}
}
//打印分析过程,包括分析栈,待分析字符
void print(int m){
int n,j;
for(n=0;n<q+1;n++){
cout<<as[n];//输出当前分析栈中的字符
}
cout<<setw(5);
for(j=m;j<20;j++){
cout<<sentence[j];//输出待分析的字符
}
cout<<endl;//回车换行
}
//非终结符与数字代码间的对应
char table1[4]={'$','S','T','U'};
//终结符与数字代码间的对应
char table2[7]={'$','a','b','(',')',',','#'};//#为句子的结束符
//判断栈顶字符是否为终结符
int judge(char m){
int i;
int j=0;//0 代表未找到,为非终结符
for(i=1;i<6;i++){
if(table2[i]==m){//找到
j=1;//m是终结符
break;//退出
}
}
return(j);//若是非终结符,j保持原值
}
//报错函数
void error(){
cout<<"错误,不是合法的句子!"<<endl;
}
//查询非终结符的数字代码
void search1(char m){
int i;
for(i=1;i<4;i++){
if(table1[i]==m){
x=i;
break;
}
}
}
//查询终结符的数字代码
void search2(char m){
int i;//
for(i=1;i<6;i++){
if(table2[i]==m){
y=i;
break;
}
}
}
void main(){
//int i=0;//控制输入待分析的字符
int p;//记录查询预测分析表后,得到的规则的数字带代码
char t,n;//t--句子中的字符; n--分析栈顶的字符
cout<<"请输入要分析的句子,以#结束:"<<endl;
cin>>sentence;//存储待分析的句子
cout<<"分析栈和输入符号的变化如下:"<<endl;
while(1){//条件不好确定,用break退出
t=sentence[i];
n=as[q];
if(judge(n)==1){//n是终结符
if(n==t){//匹配
i++;//分析下一个字符
q--;//消去匹配的栈顶字符
print(i);//打印分析栈
}
else {//无法匹配,出错
error();
break;
}
}
else{//n是非终结符,即分析栈已空
if(n=='#'){//n是句末符号
if(n==t){//分析到了句子的最后,即句子分析完毕
cout<<"句子合法,接受!"<<endl;
break;
}
else{//句子非法
error();
break;
}
}
else{//n是非终结符
search1(n);
search2(t);
p=pat[x][y];//得到预测分析表中的规则的数字代码
if(p!=0){//规则存在
fill(p);
}
else{//无规则对应
error();
break;
}
}
}
}
system("pause"); //窗口暂停,以显示结果
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -