ccompile.cpp

来自「c 语言写的C语言编译器,使用vc++6.0」· C++ 代码 · 共 1,651 行 · 第 1/2 页

CPP
1,651
字号
#include<iostream.h>
#include<fstream.h>
#include<stdlib.h>
#include<string.h>
#include <strstrea.h>
#define MAXLEN 10	//关键字的长度
#define KEYLEN 6	//关键字的个数
#define SYMLEN 17	//符号数
#define LINENUM 200		//最长代码行数


#define Getchdo    if(-1==Getch()) return -1
#define Getsymdo     if(-1==Getsym()) return -1


ifstream fin;//读取源文件
ofstream fos;//词法分析中间程序

int cc=0,lc=0;//读取字符计数器
char line[81]="\0";//读取
char ch=' ';//读取的字符
char symch[MAXLEN];//保留读取的符号
int list[400];//记录源程序的链
int listc=0;

bool meanflags;
int PreCodeLine=0;

int NextCodeLine=1;
enum Classify
{
	keywordsym,symbolsym,usrsym,numsym
}sort;		//识别单词是什么类型的



const char keyword[KEYLEN][MAXLEN]=//	记录保留字
{
	"main","int","if","else","while","const"
};
const char symbol[SYMLEN][MAXLEN]=//	记录符号
{
	"(",")","{","}","\"",",","+","-","*","/",";","<","<=",">",">=","=","=="
};

char usr[LINENUM][MAXLEN];//保存标识符
char num[LINENUM][MAXLEN];//保存数字
char sym[LINENUM][MAXLEN];//符号
char key[LINENUM][MAXLEN];//记录保留字

int usrc=0;
int numc=0;
int symc=0;
int keyc=0;
int linec=1;//源程序行号计数器

int keymc=0;//语法分析计数器
int symmc=0;
int usrmc=0;
int nummc=0;


//*****************************************************词法分析函数声明
void Init();
int Getch();
int Getsym();
int WordAns();
bool Iskeyword(); //判断symch是不是关键字
void error(int n);
struct TrueList{
char *codeElement;//当前要跳转语句地址的空间存储在这
TrueList *next;//下一个该类型空间的地址
};
TrueList *TrueHead=NULL;

//******************************************************语法分析函数声明
struct CodeList{//the code store in this list 
	char *cal;//the calulate symbol
	char *first;//the fisrt operator symbol
	char *second;//the second operator symbol
	char *destination;//the destination
	CodeList *next;//the next code
};

void GetSymbol();//读取标识符
void MeanAns();//语法分析
void Program();//程序开始
void ProPart();//分程序
void ConstDec();//常量声明
void ConstDef();//常量定义
void VarDecPart();//变量说明部分
void VarDec();//变量说明
void IdentTab();//标识符序列
void IdentTab1();//标识符序列1
void Ident();//标识符
void SemiPart();//语句部分
void Semi();//语句
void ComplexSemi();//复合语句
void SemiSeries();//语句序列
void SemiSeries1();//语句序列1
void AssignSemi();//赋值语句
void Condition();//条件
void Express();//表达式
void Trade();//项
void Trade1();//项
void Express1();//表达式1
void Factor();//因子
void ConditionSemi();//条件语句
void LoopSemi();//循环语句
int listmc=0;//语法分析时候的计数器
char *changeNumToString(int number);

//*********************************************************语义分析,代码生成
void Generate();//四元式生成函数
bool classify();//用于检测有没有没有定义的标识符
int genCode(char cal,char *first,char *second,char *destination);
int testTable()
{
	cout<<"the user defintion table"<<endl;
	for(int i=0;i<LINENUM;i++)
	{
		cout<<usr[i]<<" ";
	}
	cout<<"the number table"<<endl;
	for( i=0;i<LINENUM;i++)
	{
		cout<<num[i]<<" ";
	}
	cout<<"the symbol table"<<endl;
	for( i=0;i<LINENUM;i++)
	{
		cout<<sym[i]<<" ";
	}
	cout<<"the key table"<<endl;
	for( i=0;i<LINENUM;i++)
	{
		cout<<key[i]<<" ";
	}
	cout<<"******************************"<<endl;
	return 1;
}
void genProgram();//程序开始
void genProPart();//分程序
void genConstDec();//常量声明
void genConstDef();//常量定义
void genVarDecPart();//变量说明部分
void genVarDec();//变量说明
void genIdentTab();//标识符序列
void genIdentTab1();//标识符序列1
void genIdent();//标识符
void genSemiPart();//语句部分
void genSemi();//语句
void genComplexSemi();//复合语句
void genSemiSeries();//语句序列
void genSemiSeries1();//语句序列1
void genAssignSemi();//赋值语句
char* genCondition();//条件
char *genExpress();//表达式
char* genTrade();//项
char* genTrade1();//项
char* genExpress1();//表达式1
char* genFactor();//因子
void genConditionSemi();//条件语句
void genLoopSemi();//循环语句

char intusr[LINENUM][MAXLEN];
int intusrc=0;
CodeList *head=NULL;
int otCode();




void main()
{
//	cout<<"HELLO"<<endl;
	fin.open("code.txt");
	fos.open("codeobj.txt");
//	head=new CodeList;
//	head->next=NULL;
//	TrueHead->next=NULL;
	Init();
	if(fin)
	{
		if(WordAns()==0)
		{
			testTable();
			linec=1;
		//	MeanAns();	
		//	if(meanflags)
		//	{
				system("type codeobj.txt");
	//			cout<<endl;
				Generate();
				otCode();
	//		}
		}
		
	}
	fin.close();
	fos.close();
	cout<<endl;
	
/*
	usrc=numc=symc=keyc=0;

	for(int i=0;i<listc;i++)
	{
		switch(list[i])
		{
		case 0:
			cout<<key[keyc++];
			break;
		case 1:
			cout<<sym[symc++];
			break;
		case 2:
			cout<<usr[usrc++];
			break;
		case 3:
			cout<<num[numc++];
			break;
		case -2:
			cout<<endl;
			break;
			
		}
	}
	*/
}

//****************************************词法分析函数

void Init()
{
	for(int i=0;i<LINENUM;i++)
		for(int j=0;j<MAXLEN;j++)
	{
	 usr[i][j]='\0';
	 num[i][j]='\0';
	 sym[i][j]='\0';
	 key[i][j]='\0';
	}
}
int Getch()
{
	if(cc==lc)
	{
		list[listc++]=-2;//换行符
		if(fin.eof())
			return -1;
		cc=lc=0;
		ch='0';
		while(ch!='\n')//当为换行符和空格时候要跳过
		{
			
			if(fin.eof())
			{
				line[lc]=0;
				break;
			}
			else
			{
				ch=fin.get();
				line[lc]=ch;
				lc++;
				if(!fin.eof())//中间代码送入到codeobj.txt
					fos<<ch;
			}
		}
		linec++;
	
		if(!fin.eof())//中间代码
			fos<<linec<<'\t';
	}
	ch=line[cc];
//	cout<<ch;
	cc++;
	return 0;

}

int WordAns()
{
	
	if(!fin.eof())
	{
		fos<<linec<<'\t';

		Getsymdo;
		do{
			if(sort==keywordsym)
			{
				strcpy(key[keyc++],symch);
				list[listc++]=0;
			}
			else if(sort==symbolsym)
			{
				strcpy(sym[symc++],symch);
				list[listc++]=1;
			}
			else if(sort==usrsym)
			{
				strcpy(usr[usrc++],symch);
				list[listc++]=2;
			}
			else
			{
				strcpy(num[numc++],symch);
				list[listc++]=3;
			}
			Getsymdo;
		}while(!fin.eof() || lc!=cc);//这个条件很重要
	}
	list[listc]=-1;
	
	return 0;
}


int Getsym()
{
	int k;
	while(ch==' '||ch=='\n'||ch=='\t')                 /*忽略空格,换行和TAB*/
	{
		Getchdo;

	}
	if(ch>='a'&&ch<='z')		                   /*名字或保留字以a..z开头*/
	{
		k=0;
		do
		{
			if(k<MAXLEN)
			{
				symch[k]=ch;
				k++;
			}
			else 
			{
				error(1);
				return -1;
			}
			
			Getchdo;
			
		}while((ch>='a' && ch<='z') || (ch>='0' && ch<='9'));
		symch[k]='\0';
		/*
		*对符号类型进行判断
		*
		*if()
		*/
		if(Iskeyword())
		{
			sort=keywordsym;//	cout<<symch;//***************************************************************
			return 0;
		}
		else
		{
			sort=usrsym;//	cout<<symch;//***************************************************************
			return 0;
		}

	}
	else if(ch>='0'&&ch<='9')		                 	/*检测是否为数字,以0..9开头*/
	{
		k=0;
		do
		{
			if(k<MAXLEN)
			{
				symch[k]=ch;
				k++;
			}
			else 
			{
				error(1);
				return -1;
			}
			Getchdo;
		}while(ch>='0'&&ch<='9');
		symch[k]='\0';	//	cout<<symch;//***************************************************************
		sort=numsym;
		return 0;
	}
	else if(ch=='(')                  //检测左括号
	{
		k=0;
		sort=symbolsym;
		symch[k]=ch;
		symch[++k]='\0';//		cout<<symch;//***************************************************************
		Getchdo;
		return 0;
	}
	else if(ch==')')                  //检测右括号
	{
			k=0;
			sort=symbolsym;
			symch[k]=ch;
			symch[++k]='\0';//		cout<<symch;//***************************************************************
			Getchdo;
			return 0;
	}
	else if(ch=='{')                 //检测左大括号
	{
			k=0;
			sort=symbolsym;
			symch[k]=ch;
			symch[++k]='\0';//		cout<<symch;//***************************************************************
			Getchdo;
			return 0;
	}
	else if(ch=='}')                 //检测左大括号
	{
			k=0;
			sort=symbolsym;
			symch[k]=ch;
			symch[++k]='\0';//		cout<<symch;//***************************************************************
			Getchdo;
			return 0;
	}
	else if(ch=='+')                 //检测加号
	{
			k=0;
			sort=symbolsym;
			symch[k]=ch;
			symch[++k]='\0';//		cout<<symch;//***************************************************************
			Getchdo;
			return 0;
	}
	else if(ch=='-')                 //检测减号
	{
			k=0;
			sort=symbolsym;
			symch[k]=ch;
			symch[++k]='\0';//		cout<<symch;//***************************************************************
			Getchdo;
			return 0;
	}

	else if(ch=='*')                 //检测乘号
	{
			k=0;
			sort=symbolsym;
			symch[k]=ch;
			symch[++k]='\0';//		cout<<symch;//***************************************************************
			Getchdo;
			return 0;
	}
	else if(ch=='/')                 //检测除号
	{
			k=0;
			sort=symbolsym;
			symch[k]=ch;
			symch[++k]='\0';//		cout<<symch;//***************************************************************
			Getchdo;
			return 0;
	}
	else if(ch==';')                 //检测分号
	{
			k=0;
			sort=symbolsym;
			symch[k]=ch;
			symch[++k]='\0';//		cout<<symch;//***************************************************************
			Getchdo;
			return 0;
	}
	else if(ch==',')                 //检测逗号
	{
			k=0;
			sort=symbolsym;
			symch[k]=ch;
			symch[++k]='\0';//		cout<<symch;//***************************************************************
			Getchdo;
			return 0;
	}
	else if(ch=='\"')                 //检测引号
	{
			k=0;
			sort=symbolsym;
			symch[k]=ch;
			symch[++k]='\0';	//	cout<<symch;//***************************************************************
			Getchdo;
			return 0;
	}
	else if(ch=='=')                 //检测赋值等于号
	{
			k=0;
			symch[k++]=ch;
			sort=symbolsym;	
			Getchdo;
			if(ch=='=')					//等于
			{
				symch[k++]=ch;
						
				Getchdo;
				
			}
			symch[k]='\0';

//				cout<<symch;//***************************************************************
			
			return 0;
	}
	else if(ch=='<')                 //检测小于号
	{
			k=0;
			symch[k++]=ch;
			sort=symbolsym;		
			Getchdo;
			if(ch=='=')				//小于等于
			{
				symch[k++]=ch;
						
				Getchdo;			
			}
			symch[k]='\0';

//				cout<<symch;//***************************************************************
			return 0;
	}
	else if(ch=='>')                 //检测大于号
	{
			k=0;
			symch[k++]=ch;
			sort=symbolsym;	
			Getchdo;
			if(ch=='=')				//大于等于号
			{
				symch[k++]=ch;

				Getchdo;		
			}
				symch[k]='\0';
//					cout<<symch;//***************************************************************
			return 0;
	}
	else if(ch=='!')
	{
			k=0;
			symch[k++]=ch;
			sort=symbolsym;
			Getchdo;
			if(ch=='=')				//不等于号
			{
				symch[k++]=ch;
				Getchdo;		
			}
			else 
			{
				error(2);			//不能配成不等于号
				return -1;
			}
			symch[k]='\0';
			return 0;
		
	}

	return 0;
}

void error(int n)
{
	meanflags=false;
	cout<<"第"<<linec-1<<"出错了,error  **"<<n<<""<<endl;
}
bool Iskeyword()
{
	for(int i=0;i<KEYLEN;i++)
	{
		if(strcmp(symch,keyword[i])==0)
			return true;
	}
		return false;
}

void clear()
{
	keymc=symmc=nummc=usrmc=0;
}


//**************************************语法分析函数*****************************//

void GetSymbol()
{
	switch(list[listmc++])
	{
	case 0:
		strcpy(symch,key[keymc++]);
		sort=keywordsym;
		break;
	case 1:
		strcpy(symch,sym[symmc++]);
		sort=symbolsym;
		break;
	case 2:
		strcpy(symch,usr[usrmc++]);
		sort=usrsym;
		break;
	case 3:
		strcpy(symch,num[nummc++]);
		sort=numsym;
		break;
	case -2:
		linec++;
		GetSymbol();
		break;
	default:
		if(meanflags)
		cout<<"语法分析结束"<<endl;
	}
	
}

void MeanAns()
{
	meanflags=true;
	GetSymbol();
	Program();
}
void Program()
{
	if(!strcmp(symch,"main"))
	{
		GetSymbol();
		if(!strcmp(symch,"("))
		{
			GetSymbol();
			if(!strcmp(symch,")"))
			{
				GetSymbol();
				if(!strcmp(symch,"{"))
				{
					GetSymbol();
					ProPart();
					if(!strcmp(symch,"}"))
					{
						GetSymbol();
					}
					else
					{
						error(4);
					}
				}
				else
				{
					error(3);
				}
			}
			else
			{
				error(12);
			}

		}
		else
		{
			error(13);
		}
	
	}
	else
	{
		error(5);
	}
}

void ProPart()
{
	ConstDec();

	VarDecPart();
	if(!strcmp(symch,";"))
	{
		GetSymbol();
		SemiPart();
	}
	else
	{	//cout<<symch<<endl;////////////////////////
		//cout<<"there"<<endl;///////////////////////////
	//	cout<<symch<<endl;
		error(6);
//		SemiPart();
	}
}
void ConstDec()
{
	if(!strcmp(symch,"const"))
	{
		GetSymbol();
		ConstDef();
		if(!strcmp(symch,";"))
		{
			GetSymbol();
		}
		else
		{
			error(6);
		}
	}
}
void Ident()//judge if identity 
{
	if(sort==usrsym)
	{
		GetSymbol();
	}
	else 
	{
		error(2);
	}
}
void ConstDef()
{
	Ident();
	if(!strcmp(symch,"="))
	{
		GetSymbol();
		if(sort==3)
		{

			GetSymbol();
		}
		else
		{
			error(7);
			GetSymbol();
		}
	}
	else
	{
		GetSymbol();
		error(8);
	}

}
void VarDecPart()//变量说明部分
{
	VarDec();
	IdentTab();
}
void VarDec()
{
	if(!strcmp(symch,"int"))
	{
		GetSymbol();

	}
	else
	{
		error(9);
	}
}
void IdentTab()
{
	Ident();

	IdentTab1();
}
void IdentTab1()
{
	if(!strcmp(symch,","))
	{
		GetSymbol();
		Ident();
		IdentTab1();
	}
}
void SemiPart()//语句部分
{
	if(!strcmp(symch,"{"))
	{
		ComplexSemi();
	}
	else
		SemiSeries();
}

void Semi()//语句
{
//	cout<<"else"<<endl;
	if(sort==2)
	{
		AssignSemi();
		if(!strcmp(symch,";"))
		{
			GetSymbol();

		}
		else
		{
			error(6);
		}
	}
	else if(!strcmp(symch,"if"))
	{
		ConditionSemi();
	}
	else if(!strcmp(symch,"while"))
	{
		LoopSemi();
	}
	else
		ComplexSemi();
}
void ComplexSemi()//复合语句
{
	if(!strcmp(symch,"{"))
	{	
		GetSymbol();
		SemiSeries();

		if(!strcmp(symch,"}"))
		{
			GetSymbol();
		}
		else
			error(4);
	}
	else 
	{
		error(3);
		SemiSeries();
		GetSymbol();

⌨️ 快捷键说明

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