⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 编译原理.cpp

📁 编译原理词法分析程序
💻 CPP
字号:
/*
  Name: Lexical Analysis
  Copyright: GUN Copyleft 
  Author: Liuguo
  Class No.:1925205
  Date: 11/11/07 14:04
  Description: An experiment under course by Louie
*/
#define MAX_ATTRIBUTE_SIZE 500
#define MAX_IDENTIFIER_STACK_SIZE 100
#define MAX_IDENTIFIER_LENGTH 32
//#define TEST
#define OUTPUT "output.txt"
#define EOR -1
#define OK  0
#define LASTCONSTANT 8
#define NONE "none"
#define CONFIG "config.ini"
#define ID_ENTIFIER "[identifier]"
#define CON_STANT "[constant]"
#define SYM_BOL "[symbol]"
#define KEY_WORD "[keyword]"
#include<iostream>
#include<fstream>
#include<string>
using namespace std;

//the most useful struct
typedef struct Lnode{
	char content[10];
	struct Lnode *next;

}Lnode,*node;

//Definition Of Each Table Struct 
typedef   struct identifier{//Identifier Table struct
	char ident[MAX_IDENTIFIER_LENGTH];//identifier name
	node machine;
}identifier,*IDENTABLE;
typedef  struct constant{//Constant Table struct
	char cons[MAX_IDENTIFIER_LENGTH];
	node machine;
}constant,*CONSTABLE;
typedef  struct symbol{//Symbols table struct
	char symbols[10];
	node machine;
}symbol,*SYMBLE;
typedef  struct keywd{//keyword table struct
	char keyword[10];
	node machine;
}keywd,*KEYBLE;
typedef   struct idstack{//identifier stack struct
	IDENTABLE element;
	int *stacktop;
	int *stackbottom;
	int element_num; 
}idstack,*IDENTACK;


//do configure file check
int config_check(char *FILE_NAME)
{
	char del[32]="erase ";
	int i=6;
	ofstream pickfile(FILE_NAME,ios::app);
	pickfile.close();
	ifstream needfile(FILE_NAME);
    if(needfile.get()==-1)
	{
		cout<<"ERROR,the file "<<FILE_NAME<<" is missing!"<<endl;
		needfile.close();
		getchar();
        while(*FILE_NAME)
		{
			del[i++]=*FILE_NAME;
            FILE_NAME++;
		}
		system(del);
		return EOR;
	}
	needfile.close();
	return OK;
}
void outinit()
{
	ofstream outf(OUTPUT);
	char p[50]="/*By  刘国栋,1925205 for 编译原理 实验*/";
	int i=0;
	char s;
	while(p[i])
	{
	s=p[i++];
	outf.put(s);
	}
	outf.put('\n');
	outf.close();
}
//Table Initialization
int ident_init(IDENTABLE table)
{
	 char ch;
	 char str[20]={'\0'};
	 Lnode *p,*q;
	 int i=0;
     ifstream myfile(CONFIG);
	 table->machine=new Lnode;
	 p=q=table->machine;
     ifstream fileopen(CONFIG);
	while(!fileopen.eof())//loacting the load position
	{
		for(;i>0;i--) str[i]='\0';//initlise cache
		while(1)
		{
			fileopen.get(ch);
			if(ch=='\n'||fileopen.eof())
			  break;
			str[i++]=ch;
		}
		if(strcmp(str,ID_ENTIFIER)==0)
			break;
	}
	//in position
	for(;i>0;i--) str[i-1]='\0'; //need do it again
     while(1)
	 {

		 fileopen.get(ch);

		 if(((ch!=' ')&&(ch!='\n'))&&!fileopen.eof())//字符不是空格或换行且没有到文件尾
		    str[i++]=ch;
		 if (str[0]!='\0'&&((ch==' ')||(ch=='\n')))
		 {
			
			 p->next=q; p=p->next;
			 strcpy(p->content,str);//此处赋值
             q=new Lnode;
		 }
		 if(ch=='\n')
			 break;
		 if(ch==' ')
			 for(;i>0;i--) 
				 str[i-1]='\0';
		 if(fileopen.eof())
		 {
			 fileopen.close();
			 return OK;
		 }

	 }
	 p->next=NULL;//分配后指针不为0
#ifdef TEST
	 p=table->machine;
	 while(p)
	 {
          cout<<p->content;
		  p=p->next;
	 }
	 cout<<endl;
#endif
	 		
	 return OK;
}
int cons_init(CONSTABLE table)
{
	 char ch;
	 char str[20]={'\0'};
	 Lnode *p,*q;
	 int i=0;
	 table->machine=new Lnode;
	 p=q=table->machine;
     ifstream fileopen(CONFIG);
	while(!fileopen.eof())//loacting the load position
	{
		for(;i>0;i--) str[i]='\0';//initlise cache
		while(1)
		{
			fileopen.get(ch);
			if(ch=='\n'||fileopen.eof())
			  break;
			str[i++]=ch;
		}
		if(strcmp(str,CON_STANT)==0)
			break;
	}
	//in position
	 for(;i>0;i--) str[i-1]='\0'; //need do it again
     while(1)
	 {

		 fileopen.get(ch);

		 if(((ch!=' ')&&(ch!='\n'))&&!fileopen.eof())//字符不是空格或换行且没有到文件尾
		    str[i++]=ch;
		 if (str[0]!='\0'&&((ch==' ')||(ch=='\n')))
		 {
			
			 p->next=q; p=p->next;
			 strcpy(p->content,str);//此处赋值
             q=new Lnode;
		 }
		 if(ch=='\n')
			 break;
		 if(ch==' ')
			 for(;i>0;i--) 
				 str[i-1]='\0';
		 if(fileopen.eof())
		 {
			 fileopen.close();
			 return OK;
		 }

	 }
	 p->next=NULL;//分配后指针不为0
#ifdef TEST
	 p=table->machine;
	 while(p)
	 {
          cout<<p->content;
		  p=p->next;
	 }
	 cout<<endl;
#endif
	return OK;
}
int sym_init(SYMBLE table)
{
	 char ch;
	 char str[20]={'\0'};
	 Lnode *p,*q,*front;
	 int i=0;
	//start of position
	ifstream fileopen(CONFIG);
	while(!fileopen.eof())//loacting the load position
	{
		for(;i>0;i--) str[i]='\0';//initlise cache
		while(1)
		{
			fileopen.get(ch);
			if(ch=='\n'||fileopen.eof())
			  break;
			str[i++]=ch;
		}
		if(strcmp(str,SYM_BOL)==0)
			break;
	}//end of position
	for(int k=0;k<19;k++)
	{
	     table->machine=new Lnode;
	     p=q=table->machine;
	//in position
		 for(;i>0;i--) str[i-1]='\0'; //need do it again
		 while(1)
		 {

			 fileopen.get(ch);

			if(((ch!=' ')&&(ch!='\n'))&&!fileopen.eof())//字符不是空格或换行且没有到文件尾
				str[i++]=ch;
			if (str[0]!='\0'&&((ch==' ')||(ch=='\n')))
			{
			
				 p->next=q;front=p; p=p->next;
				strcpy(p->content,str);//此处赋值
				q=new Lnode;
			}
			if(ch=='\n')
				 break;
			 if(ch==' ')
				 for(;i>0;i--) 
					 str[i-1]='\0';
			if(fileopen.eof())
			{
				 fileopen.close();
				return OK;
			}

		 }
		 strcpy(table->symbols,p->content);
		 delete(p);//分配后指针不为0
		 front->next=NULL;
	#ifdef TEST
		 p=table->machine;
		while(p)
		 {
          cout<<p->content;
		  p=p->next;
		}
		cout<<table->symbols<<endl;
	#endif
		table++;
	}

	return OK;
}
int key_init(KEYBLE table)
{
	char ch;
    char str[20]={'\0'};
	Lnode *p,*q,*front;
	int i=0;
	//start of position
	ifstream fileopen(CONFIG);
	while(!fileopen.eof())//loacting the load position
	{
		for(;i>0;i--) str[i]='\0';//initlise cache
		while(1)
		{
			fileopen.get(ch);
			if(ch=='\n'||fileopen.eof())
			  break;
			str[i++]=ch;
		}
		if(strcmp(str,KEY_WORD)==0)
			break;
	}//end of position
	for(int k=0;k<8;k++)
	{
	     table->machine=new Lnode;
	     p=q=table->machine;
	//in position
		 for(;i>0;i--) str[i-1]='\0'; //need do it again
		 while(1)
		 {

			 fileopen.get(ch);

			if(((ch!=' ')&&(ch!='\n'))&&!fileopen.eof())//字符不是空格或换行且没有到文件尾
				str[i++]=ch;
			if (str[0]!='\0'&&((ch==' ')||(ch=='\n')))
			{
			
				 p->next=q; front=p;p=p->next;
				strcpy(p->content,str);//此处赋值
				q=new Lnode;
			}
			if(ch=='\n')
				 break;
			 if(ch==' ')
				 for(;i>0;i--) 
					 str[i-1]='\0';
			if(fileopen.eof())
			{
				 fileopen.close();
				return OK;
			}

		 }
		 strcpy(table->keyword,p->content);
		 delete(p);//分配后指针不为0
		 front->next=NULL;
	#ifdef TEST
		 p=table->machine;
		while(p)
		 {
          cout<<p->content;
		  p=p->next;
		}
		cout<<table->keyword<<endl;
	#endif
		table++;
	}
	return OK;
}
//输出处理
void outp(char *content )
{
	int i=0;
	char s;
	ofstream outf(OUTPUT,ios::app);
	while(content[i])
	{
	s=content[i++];
#ifdef TEST
	cout<<s;
#endif
	outf.put(s);
	}
}
//字符处理
int getch(IDENTABLE itable,CONSTABLE ctable,SYMBLE stable,KEYBLE ktable,char *FILE_NAME)
{
	char ch;
	char cp[2]={'\0'};
	int j;
	Lnode *p;
	IDENTABLE it=itable;
	CONSTABLE ct=ctable;
	SYMBLE st=stable;
	KEYBLE kt=ktable;
	ofstream outfile(OUTPUT,ios::app);
	int last_flag=0;
	char ss[10]={'\0'};
	int i=0;
	int dArray=0;
	//LASTSYMBOL
	//LASTCONSTANT
	//LASTCHARAC
	//LASTSPACE
	int wline=1;//
	ifstream getfile(FILE_NAME);
	getfile.get(ch);
	while(1)//ready to load characters
	{
		//if(getfile.eof())
		if(getfile.eof())
			break;
		if(last_flag==1)
		{
			while(1)
			{
				getfile.get(ch);
				if(ch=='*')
				{
					getfile.get(ch);
					if(ch=='/')
					{	last_flag=0;  
						getfile.get(ch);
						if (getfile.eof())
							return OK;
						break;
					}
					else if(ch=='\n')
						wline++;
					else if(getfile.eof ())
						return OK;
					else 
						continue;
				}
				continue;

			}
		}
		if(ch==' '||ch=='\n'||ch=='	')
		{
			if(ch=='\n') wline++;
			getfile.get(ch);
			continue;
		}
		if((ch>='a'&&ch<='z')||(ch>='A'&&ch<='Z'))
		{
			ss[i++]=ch;
			while(1)
			{
				getfile.get(ch);
				if((ch>='a'&&ch<='z')||(ch>='A'&&ch<='Z')||(ch>='0'&&ch<='9'))
				{
					ss[i++]=ch;
					continue;
				}
				for(j=0,kt=ktable;j<8;j++,kt++)
					if(strcmp(ss,kt->keyword)==0)
						break;//if检查是否为关键字,压入属性表序列
				if(j<8)
				{
					p=kt->machine;
					while(p)
					{
						outp(p->content);
						//cout<<p->content;
						outp("  ");
						//cout<<"  ";
						p=p->next;
					}
					outp(kt->keyword);
					outp("\n");
					//cout<<kt->keyword<<endl;

				}
				else 
				{
					p=it->machine;
					while(p)
					{
						outp(p->content);
						//cout<<p->content;
						outp("  ");
						//cout<<"  ";
						p=p->next;
					}
					outp(ss);
					outp("\n");
					//cout<<ss<<endl;
					//标识符属性字输出
				}
				//else不是,制造标识符表插入属性表序列,if(last_identifier=1)压入标识符栈,last_identifier=0;if(last_identifier=0)
				//查找标识栈,存在pass,不存在ERROR;
				for(;i>0;i--)
				      ss[i-1]='\0';
				break;
			}
			continue;
		}
		else if(ch>='0'&&ch<='9')
		{
			ss[i++]=ch;
			while(1)
			{
				if(getfile.eof())
				{
					cout<<"文件结尾符错误"<<endl;
					return EOR;
				}
				getfile.get(ch);
				if((ch>='0'&&ch<='9')||ch=='.')
				{
					ss[i++]=ch;
					continue;
				}
				else if((ch>='a'&&ch<='z')||(ch>='A'&&ch<='Z'))
				{
					cout<<"非法的标识符位于"<<wline<<"行"<<endl;
					cout<<"标识符首位不能为数字"<<endl;
					return EOR;
				}
				else
				{
					p=ct->machine;
					while(p)
					{
						outp(p->content);
						//cout<<p->content;
						outp("  ");
						//cout<<"  ";
						p=p->next;
					}
					outp(ss);
					outp("\n");
					//cout<<ss<<endl;
                 //查造常量表,压入属性字序列
				}
				for(;i>0;i--)
				      ss[i-1]='\0';
				break;
			}
			continue;
		}
		else
		{
			ss[i++]=ch;
            for(j=0,st=stable;j<19;j++,st++)
				if(strcmp(ss,st->symbols)==0)
					break;
			if(j>=19)
			{
				cout<<"非法字符!";
				return EOR;
			}
			if(j==16)
				dArray=1;
				getfile.get(ch);
				if (!((ch>='a'&&ch<='z')||(ch>='A'&&ch<='Z'))&&!(ch>='0'&&ch<='9')&&(ch!=' ')&&(ch!='\n')&&!getfile.eof())
				{
					ss[i++]=ch;
					cp[0]=ch;
					for(j=0,st=stable;j<19;j++,st++)
						if(strcmp(cp,st->symbols)==0)	break;
					if(j>=19)
					{	cout<<"非法字符!";return EOR;		}
					if(j==15&&dArray==1)
					{
						cout<<"该程序不允许二维数组的出现,但是偏偏居然在"<<wline<<"行出现了"<<endl;
							return EOR;
					}
					else dArray=0;
					if(strcmp(ss,"/*")==0)
					{	
						last_flag=1;
						for(;i>0;i--)
						ss[i-1]='\0';
					    continue;
					}
					for(j=0,st=stable;j<19;j++,st++)
						if(strcmp(ss,st->symbols)==0)	break;
					if(j<19)
					{
						p=st->machine;
						while(p)
						{
							outp(p->content);
							//cout<<p->content;
							outp("  ");
							//cout<<"  ";
							p=p->next;
						}
						outp(st->symbols);
						outp("\n");
						//cout<<st->symbols<<endl;
						for(;i>0;i--)
							ss[i-1]='\0';
					}
					else
					{
						cp[0]=ss[0];
						for(j=0,st=stable;j<19;j++,st++)
							if(strcmp(cp,st->symbols)==0)	break;
						if(j<19)
						{
							p=st->machine;
							while(p)
							{
								outp(p->content);
								//cout<<p->content;
								outp("  ");
								//cout<<"  ";
								p=p->next;
							}
							outp(st->symbols);
							outp("\n");
							//cout<<st->symbols<<endl;

							for(;i>0;i--)
								ss[i-1]='\0';
						continue;
						}
					}
				}//end of if
				for(j=0,st=stable;j<19;j++,st++)
				if(strcmp(ss,st->symbols)==0)	break;
				p=st->machine;
				while(p)
				{
					outp(p->content);
					outp("  ");
					//cout<<p->content;
					//cout<<"  ";
					p=p->next;
				}
				outp(st->symbols);
				outp("\n");
				//cout<<st->symbols<<endl;
				for(;i>0;i--)
					ss[i-1]='\0';
				continue;
		}//endof else



	}//end of while
	
    return OK;
}

int main(int argc,char **args)
{
	char FILE_NAME[32];
	//memory allocation for identifier stack
	IDENTACK istack=new idstack[MAX_IDENTIFIER_STACK_SIZE];
	identifier *ident_ble=new identifier;
	constant *const_ble= new constant;
	symbol *sym_ble=new symbol[19];
	keywd *key_ble=new keywd[8];
	if(config_check(CONFIG))
		return 0;
	//初始化输出文件
    outinit();
	//initialization entrance
	if(!(!ident_init(ident_ble)&&!cons_init(const_ble)&&!sym_init(sym_ble)&&!key_init(key_ble)))
	{
		cout<<"Error,the founction initialization failed!"<<endl
			  <<"Press any key to exit...";
		getchar();
		return 0;
	}

	//参数传递判断
	if(argc==1)
	{
		cout<<"FILE_NAME:";
		cin>>FILE_NAME;
		getchar();
	}
    else if(argc!=2)
	{
		cout<<"Error,agrument is missing!";
		return 0;
	}
	else
		strcpy(FILE_NAME,*(++args));
	if(config_check(FILE_NAME))
		return 0;
	if(getch(ident_ble,const_ble,sym_ble,key_ble,FILE_NAME))
		cout<<"Error";
	system(OUTPUT);
	return 0;

}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -