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

📄 semantic.cpp

📁 词法语法语义编译器
💻 CPP
📖 第 1 页 / 共 2 页
字号:
// Semantic.cpp: implementation of the CSemantic class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "scanner.h"
#include "Semantic.h"
#include "Parsing.h"

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

/**
 * 语义分析构造函数
 *
 * @param  pWordCode			字符表数组
 * @param  pTokenFile			token串头指针
 * @param  pSymbolTable			符号表头指针
 * @param  pErrorCollection		错误信息头指针
 *
 */
CSemantic::CSemantic(const char *pWordCode[],
					 PTokenNode pTokenFile,
					 PSTable pSymbolTable,
					 PFSymbol pFSymbol,
					 PErrorNode pErrorCollection)
{
	m_strSourceFile="";
	m_bUseCurToken=true;
	m_pCurToken=NULL;
	m_pFSymbol=pFSymbol;
	this->m_pMorpheme=new CMorpheme(pWordCode,pTokenFile,pSymbolTable,pErrorCollection);
	this->m_pSymbolTable=pSymbolTable;
	for (int i=0;i<KEYWORDCOUNT+1;i++)
	{
		this->m_pWordCode[i]=pWordCode[i];
	}
	InitPFSymbol();
}

/**
 * 语义分析构造函数
 *
 * @param  pWordCode			字符表数组
 * @param  pTokenFile			token串头指针
 * @param  pSymbolTable			符号表头指针
 * @param  pErrorCollection		错误信息头指针
 * @param  strSourceFile		源程序文件路径
 *
 */
CSemantic::CSemantic(const char *pWordCode[],
					 PTokenNode pTokenFile,
					 PSTable pSymbolTable,
					 PFSymbol pFSymbol,
					 PErrorNode pErrorCollection,
					 CString strSourceFile)
{
	m_strSourceFile=strSourceFile;
	m_bUseCurToken=true;
	m_pCurToken=NULL;
	m_pFSymbol=pFSymbol;
	this->m_pMorpheme=new CMorpheme(pWordCode,pTokenFile,pSymbolTable,pErrorCollection,strSourceFile);
	this->m_pSymbolTable=pSymbolTable;
	for (int i=0;i<KEYWORDCOUNT+1;i++)
	{
		this->m_pWordCode[i]=pWordCode[i];
	}

	InitPFSymbol();
}

/**
 * 初始化四元式链
 *
 */
void CSemantic::InitPFSymbol()
{
	PFSymbol pFS=NULL;
	if (this->m_pFSymbol->next!=NULL)
	{
		while (m_pFSymbol->next!=NULL)
		{
			pFS=m_pFSymbol->next;
			m_pFSymbol->next=pFS->next;
			delete pFS;
		}
	}

	this->m_pFSymbol->next=new FSymbol;
	m_pCurFS=m_pFSymbol->next;
	m_pCurFS->no=1;
	m_pCurFS->ag1=NULL;
	m_pCurFS->ag2=NULL;
	m_pCurFS->next=NULL;
	m_pCurFS->result=NULL;

}

CSemantic::~CSemantic()
{

}

/**
 * 获取下一个token字
 *
 * @param	PTokenNode &pToken		token字引用
 *
 * @return  bool					F:文件分析完毕
 *
 */
bool CSemantic::GetNextToken(PTokenNode &pToken)
{
	bool returnValue=true;

	if (this->m_bUseCurToken)
	{
		returnValue=this->m_pMorpheme->StepMorpheme(m_pCurToken,this->m_strSourceFile);		
	}

	pToken=this->m_pCurToken;
	this->m_bUseCurToken=true;

	return returnValue;
}

/**
 * 当前获取的token字没被用
 *
 */
void CSemantic::NoUseCurToken()
{
	this->m_bUseCurToken=false;
}

/**
 * 连接两个四元式链,链首以pFS2开始
 *
 * @param	PFSymbol pFS1			四元式一
 * @param	PFSymbol pFS2			四元式二
 *
 * @return	PFSymbol				连接链首指针
 *
 */
PFSymbol CSemantic::Merg(PFSymbol pFS1,PFSymbol pFS2)
{
	if (pFS2==NULL) return pFS1;
	else
	{
		PFSymbol pFS=pFS2;
		while (pFS->result!=NULL && pFS->result->type==PF && pFS->result->value.fSymbol!=NULL)
		{
			pFS=pFS->result->value.fSymbol;
		}

		if (pFS->result==NULL)
		{
			pFS->result=new FSAG;
			pFS->result->des=NULL;
			pFS->result->type=PF;
			pFS->result->value.fSymbol=pFS1;
		}
		else
		{
			pFS->result->value.fSymbol=pFS1;
			pFS->result->type=PF;
		}

		return pFS2;
	}
}

/**
 * 将nextFS填入pFS的第四个分量
 *
 * @param	PFSymbol pFS			四元式一
 * @param	PFSymbol nextFS			四元式二
 *
 * @return	bool					操作结果
 *
 */
bool CSemantic::BackPatch(PFSymbol pFS,PFSymbol nextFS)
{
	PFSymbol q,Q;
	char ch[10];
	Q=pFS;
	while (Q!=NULL)
	{
		if (Q->result==NULL)
		{
			Q->result=new FSAG;
			itoa(nextFS->no,ch,10);
			Q->result->des=new char[strlen(ch)+1];
			strcpy(Q->result->des,ch);
			Q->result->type=PF;
			Q->result->value.fSymbol=nextFS;
			break;
		}
		else
		{
			if (Q->result->type!=PF) break;

			q=Q->result->value.fSymbol;
			itoa(nextFS->no,ch,10);
			Q->result->des=new char[strlen(ch)+1];
			strcpy(Q->result->des,ch);
			Q->result->value.fSymbol=nextFS;
			Q=q;
		}
	}

	return true;
}

/**
 * 获取当前要生成的四元式
 *
 */
PFSymbol CSemantic::GetCurPFS()
{
	return this->m_pCurFS;
}

/**
 * 添加错误信息
 *
 * @param	const char *description			错误信息描述
 *
 */
void CSemantic::AddError(const char *description)
{
	this->m_pMorpheme->AddError(description,this->m_pMorpheme->GetCurRow());
}

/**
 * 翻译<AE>->i+i|i-i
 *
 * @param	PTokenNode pToken			token字
 *
 */
PFSAG CSemantic::Ae(PTokenNode pToken)
{
	char ch[10];EOP op;
	PFSAG ag1=NULL,ag2=NULL;
	PFSAG result=new FSAG;
	result->des="Temp";
	result->type=ST;

	if (strcmp(this->m_pWordCode[pToken->keycode],"identifier")!=0 && 
		strcmp(this->m_pWordCode[pToken->keycode],"constfloat")!=0 &&
		strcmp(this->m_pWordCode[pToken->keycode],"constint")!=0)
	{
		this->AddError("赋值表达式错误!");
		this->NoUseCurToken();
		return NULL;
	}
	ag1=new FSAG;
	if (strcmp(this->m_pWordCode[pToken->keycode],"identifier")==0)
	{
		ag1->des=this->GetIDName(pToken);
		ag1->type=PT;
		ag1->value.token=pToken;
	}
	else
	{ 
		itoa((int)this->m_pSymbolTable->sSubTable[pToken->strId-1].val,ch,10);
		ag1->des=new char[strlen(ch)+1];
		strcpy(ag1->des,ch);
		ag1->type=ST;
		ag1->value.value=this->m_pSymbolTable->sSubTable[pToken->strId-1].val;
	}

	GetNextToken(pToken);
	if (strcmp(this->m_pWordCode[pToken->keycode],"+")!=0 && 
		strcmp(this->m_pWordCode[pToken->keycode],"-")!=0)
	{
		this->NoUseCurToken();
		Gencode(GetOP(":="),ag1,NULL,result);
		return result;
	}
	op=GetOP(this->m_pWordCode[pToken->keycode]);
	GetNextToken(pToken);
	if (strcmp(this->m_pWordCode[pToken->keycode],"identifier")!=0 && 
		strcmp(this->m_pWordCode[pToken->keycode],"constfloat")!=0 &&
		strcmp(this->m_pWordCode[pToken->keycode],"constint")!=0)
	{
		this->AddError("赋值表达式错误!");
		this->NoUseCurToken();
		Gencode(GetOP(":="),ag1,NULL,result);
		return result;
	}
	ag2=new FSAG;
	if (strcmp(this->m_pWordCode[pToken->keycode],"identifier")==0)
	{
		ag2->des=this->GetIDName(pToken);
		ag2->type=PT;
		ag2->value.token=pToken;
	}
	else
	{ 
		itoa((int)this->m_pSymbolTable->sSubTable[pToken->strId-1].val,ch,10);
		ag2->des=new char[strlen(ch)+1];
		strcpy(ag2->des,ch);
		ag2->type=ST;
		ag2->value.value=this->m_pSymbolTable->sSubTable[pToken->strId-1].val;
	}
	Gencode(op,ag1,ag2,result);
	return result;
}

/**
 * 翻译<BE>-><BT>(or<BE>|e)
 *
 * @param	PTokenNode pToken			token字
 * @param	PFSymbol &pTC				真出口
 * @param	PFSymbol &pFC				假出口
 *
 */
void CSemantic::Be(PTokenNode pToken,PFSymbol &pTC,PFSymbol &pFC)
{
	PFSymbol btTC=NULL,btFC=NULL,beTC=NULL,beFC=NULL;
	PTokenNode token=NULL;
	const char *str=this->m_pWordCode[pToken->keycode];
	if (strcmp(str,"not")==0 || strcmp(str,"(")==0 || strcmp(str,"identifier")==0)
	{
		Bt(pToken,btTC,btFC);
		this->BackPatch(btFC,GetCurPFS());
		this->GetNextToken(token);
		if (strcmp(this->m_pWordCode[token->keycode],"or")==0)
		{
			this->GetNextToken(token);
			Be(token,beTC,beFC);
			pTC=this->Merg(btTC,beTC);
			pFC=beFC;
		}
		else
		{
			pTC=btTC;
			pFC=btFC;
			this->NoUseCurToken();
		}
	}
	else
	{
		this->AddError("条件表达式错误!");
		this->NoUseCurToken();
	}
}

/**
 * 翻译<BT>-><BF>(and<BT>|e)
 *
 * @param	PTokenNode pToken			token字
 * @param	PFSymbol &pTC				真出口
 * @param	PFSymbol &pFC				假出口
 *
 */
void CSemantic::Bt(PTokenNode pToken,PFSymbol &pTC,PFSymbol &pFC)
{
	PFSymbol bfTC=NULL,bfFC=NULL,btTC=NULL,btFC=NULL;
	PTokenNode token=NULL;
	const char *str=this->m_pWordCode[pToken->keycode];
	if (strcmp(str,"not")==0 || strcmp(str,"(")==0 || strcmp(str,"identifier")==0)
	{
		Bf(pToken,bfTC,bfFC);
		BackPatch(bfTC,this->GetCurPFS());
		GetNextToken(token);
		if (strcmp(this->m_pWordCode[token->keycode],"and")==0)
		{
			GetNextToken(token);
			Bt(token,btTC,btFC);
			pFC=Merg(btFC,bfFC);
			pTC=btTC;
		}
		else
		{
			pTC=bfTC;
			pFC=bfFC;
			this->NoUseCurToken();
		}
	}
	else
	{
		this->AddError("条件表达式错误!");
		this->NoUseCurToken();
	}
}

/**
 * 生成四元式
 *
 * @param	EOP op					操作符
 * @param	PFSAG ag1				运算对象一
 * @param	PFSAG ag1				运算对象二
 * @param	PFSAG result			运算结果
 *
 */	
void CSemantic::Gencode(EOP op,PFSAG ag1,PFSAG ag2,PFSAG result)
{
	PFSymbol pFS=new FSymbol;
	pFS->next=NULL;
	pFS->ag1=NULL;
	pFS->ag2=NULL;
	pFS->result=NULL;

	m_pCurFS->op=op;
	m_pCurFS->ag1=ag1;
	m_pCurFS->ag2=ag2;
	m_pCurFS->result=result;

	this->m_pCurFS->next=pFS;
	pFS->no=this->m_pCurFS->no+1;

	this->m_pCurFS=pFS;
}

/**
 * 获取pToken的标示名称
 *
 * @param	PTokenNode pToken			token字
 *
 */	
char *CSemantic::GetIDName(PTokenNode pToken)
{
	if (strcmp(this->m_pWordCode[pToken->keycode],"identifier")==0)
	{
		unsigned int istart=this->m_pSymbolTable->sSubTable[pToken->strId-1].name.headp;
		unsigned int ilen=this->m_pSymbolTable->sSubTable[pToken->strId-1].name.length;
		char *str=new char[ilen+1];		
		for (int i=0;i<ilen;i++)
		{
			str[i]=this->m_pSymbolTable->stringTable[istart+i];
		}
		str[ilen]='\0';
		return str;
	}
	else return NULL;
}

/**
 * 翻译<BF>->not<BF>
 *		   ->'('<BE>')'
 *		   ->i(rop i|e)
 *
 * @param	PTokenNode pToken			token字
 * @param	PFSymbol &pTC				真出口
 * @param	PFSymbol &pFC				假出口
 *
 */	
void CSemantic::Bf(PTokenNode pToken,PFSymbol &pTC,PFSymbol &pFC)
{
	PFSymbol bfTC=NULL,bfFC=NULL;
	PTokenNode token=NULL;
	const char *str=this->m_pWordCode[pToken->keycode];
	if (strcmp(str,"not")==0)
	{
		GetNextToken(token);
		Bf(token,bfTC,bfFC);
		pTC=bfFC;
		pFC=bfTC;
	}
	else if (strcmp(str,"(")==0)
	{
		GetNextToken(token);
		Be(token,pTC,pFC);
		GetNextToken(token);
		if (strcmp(this->m_pWordCode[token->keycode],")")!=0) 
		{
			this->AddError("缺少)");
			this->NoUseCurToken();
		}
	}
	else if (strcmp(str,"identifier")==0)
	{
		PFSAG pFSAG1=new FSAG;
		pFSAG1->type=PT;
		pFSAG1->value.token=pToken;

⌨️ 快捷键说明

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