编译原理 LL(1)文法源代码
时间:2025-02-21
时间:2025-02-21
纯LL1文法源代码,供参考使用
LL(1)文法(源代码) #include "stdio.h" #include "stdlib.h"
#define MaxRuleNum 8 #define MaxVnNum 5 #define MaxVtNum 5
#define MaxStackDepth 20 #define MaxPLength 20 #define MaxStLength 50
struct pRNode /*产生式右部结构*/ {
int rCursor;
struct pRNode *next; };
struct pNode {
int lCursor;
int rLength; /*右部长度*/
struct pRNode *rHead; /*右部结点头指针*/ };
char Vn[MaxVnNum + 1]; /*非终结符集*/ int vnNum;
char Vt[MaxVtNum + 1]; /*终结符集*/ int vtNum;
struct pNode P[MaxRuleNum]; int PNum;
char buffer[MaxPLength + 1]; char ch;
char st[MaxStLength]; /*要分析的符号串*/
struct collectNode {
int nVt;
struct collectNode *next; };
struct collectNode* first[MaxVnNum + 1]; /*first集*/ struct collectNode* follow[MaxVnNum + 1]; /*follow集*/
纯LL1文法源代码,供参考使用
int analyseTable[MaxVnNum + 1][MaxVtNum + 1 + 1];
int analyseStack[MaxStackDepth + 1]; /*分析栈*/ int topAnalyse; /*分析栈顶*/
void Init();/*初始化*/ int IndexCh(char ch);
void InputVt(); /*输入终结符*/ void InputVn();/*输入非终结符*/
void ShowChArray(char* collect, int num);/*输出Vn或Vt的内容*/ void InputP();/*产生式输入*/
bool CheckP(char * st);/*判断产生式正确性*/ void First(int U);
void AddFirst(int U, int nCh); /*加入first集*/ bool HaveEmpty(int nVn);
void Follow(int V);/*计算follow集*/ void AddFollow(int V, int nCh, int kind);
void ShowCollect(struct collectNode **collect);/*输出first或follow集*/ void FirstFollow();/*计算first和follow*/ void CreateAT();/*构造预测分析表*/ void ShowAT();/*输出分析表*/ void Identify(char *st); void InitStack(); void ShowStack(); void Pop();
void Push(int r);
void main(void) {
char todo,ch;
Init();
InputVn(); InputVt(); InputP();
getchar();
FirstFollow();
printf("所得first集为:"); ShowCollect(first);
printf("所得follow集为:"); ShowCollect(follow);
纯LL1文法源代码,供参考使用
CreateA T();
ShowA T();
todo = 'y';
while('y' == todo)
{
printf("\n是否继续进行句型分析?(y / n):"); todo = getchar();
while('y' != todo && 'n' != todo)
{
printf("\n(y / n)? ");
todo = getchar();
}
if('y' == todo)
{
int i;
InitStack();
printf("请输入符号串(以#结束) : ");
ch = getchar();
i = 0;
while('#' != ch && i < MaxStLength)
{
if(' ' != ch && '\n' != ch)
{
st[i++] = ch;
}
ch = getchar();
}
if('#' == ch && i < MaxStLength)
{
st[i] = ch;
Identify(st);
}
else
printf("输入出错!\n");
}
}
getchar();
}
void Init()
{
纯LL1文法源代码,供参考使用
int i,j;
vnNum = 0; vtNum = 0; PNum = 0;
for(i = 0; i <= MaxVnNum; i++) Vn[i] = '\0';
for(i = 0; i <= MaxVtNum; i++) Vt[i] = '\0';
for(i = 0; i < MaxRuleNum; i++) {
P[i].lCursor = NULL; P[i].rHead = NULL; P[i].rLength = 0; }
PNum = 0;
for(i = 0; i <= MaxPLength; i++) buffer[i] = '\0';
for(i = 0; i < MaxVnNum; i++) {
first[i] = NULL; follow[i] = NULL; }
for(i = 0; i <= MaxVnNum; i++) {
for(j = 0; j <= MaxVnNum + 1; j++) analyseTable[i][j] = -1; } }
int IndexCh(char ch) {
int n;
n = 0; /*is Vn?*/
while(ch != Vn[n] && '\0' != Vn[n]) n++;
if('\0' != Vn[n]) return 100 + n; n = 0; /*is Vt?*/
while(ch != Vt[n] && '\0' != Vt[n]) n++;
if('\0' != Vt[n]) return n; return -1; }
纯LL1文法源代码,供参考使用
/*输出Vn或Vt的内容*/
void ShowChArray(char* collect) {
int k = 0;
while('\0' != collect[k]) {
printf(" %c ", collect[k++]); }
printf("\n"); }
/*输入非终结符*/ void InputVn() {
int inErr = 1; int n,k; char ch; while(inErr) {
printf("\n请输入所有的非终结符,注意:");
printf("请将开始符放在第一位,并以#号结束:\n"); ch = ' '; n = 0;
/*初始化数组*/
while(n < MaxVnNum) {
Vn[n++] = '\0'; } n = 0;
while(('#' != ch) && (n < MaxVnNum)) {
if(' ' != ch && '\n' != ch && -1 == IndexCh(ch)) {
Vn[n++] = ch; vnNum++; }
ch = getchar(); }
Vn[n] = '#'; /*以“#”标志结束用于判断长度是否合法*/ k = n; if('#' != ch) {
if( '#' != (ch = getchar())) {
while('#' != (ch = getchar()))
纯LL1文法源代码,供参考使用
;
printf("\n符号数目超过限制!\n"); inErr = 1; continue; } }
/*正确性确认,正确则,执行下下面,否则重新输入*/ Vn[k] = '\0';
ShowChArray(Vn); ch = ' ';
while('y' != ch && 'n' != ch) {
if('\n' != ch) {
printf("输入正确确认?(y/n):"); }
scanf("%c", &ch); }
if('n' == ch) {
printf("录入错误重新输入!\n"); inErr = 1; } else {
inErr = 0; } } }
/*输入终结符*/ void InputVt() {
int inErr = 1; int n,k; char ch; while(inErr) {
printf("\n请输入所有的终结符,注意:"); printf("以#号结束:\n"); ch = ' '; n = 0;
/*初始化数组*/
while(n < M …… 此处隐藏:7417字,全部文档内容请下载后查看。喜欢就下载吧 ……
上一篇:怎么把小说下载到iphone
下一篇:信息中心机房上墙制度