预测分析表LL(1)文法

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#define N 20
char warehouse[N];
char *nproduce="0";
char *forecast[5][8]={
 "TH","0","0","0","0","TH","0","0",      // 0表示没有产生式
 "0","+TH","-TH","0","0","0","e","e", //e表示产生式为空产生式
 "FP","0","0","0","0","FP","0","0",
 "0","e","e","*FP","/FP","0","e","e",
 "i","0","0","0","0","(E)","0","0"
 };  //预测分析表
char ensymbol[8]={'i','+','-','*','/','(',')','#'};    //终结符
char nensymbol[5]={'E','H','T','P','F'}; //非终结符

void print()
{
 printf("0 express no express grammar /n");
 printf("the meaning of e is null /n");
 printf("this is a forecast down /n");
 printf("the produce type : /n");
 printf("E-->TH /nH-->+TH|-TH|e /n");
 printf("T-->FP /nP-->*FP|/FP|e /n");
 printf("f-->i|(E) /n");
 printf("nensymbol have: /n");
 for(int i=0;i<5;i++)
  printf("%c /t",nensymbol[i]);
 printf("/nensymbol have: /n");
 for(int j=0;j<8;j++)
  printf("%c /t",ensymbol[j]);
 printf("/nthe forecast is: /n");
 for(int p=0;p<5;p++)
 {
  for(int q=0;q<8;q++)
   printf("%s /t",forecast[p][q]);
  printf("/n");
 }
}   //打印预测分析表的说明和解释
int strcmp(char s1[],char s2[])
{
 int i=0;
 if(s1[i]!='/0')
  if(s1[i]==s2[i])
  {
   i++;
  }
  else
  {
   return(0);
  }
 else
 {
  if(s2[i]=='/0')
   return(1);
  else
   return(0);
 }
}  //字符串的比较

void print1(char s1[],char s2[],int n)
{
 int i=0;
 for(i;i<=n;i++)
 {
  printf("%c",s1[i]);
 }
 printf("/t/t/t/t");
 printf("%s",s2);
 printf("/n");
}     //打印表达式的推到过程
void main()
{
 char s[N-1],X,a,ch;
 int b,q,p;
 int len;
 b=q=p=0;   //初始化
 print(); //打印预测分析表
 printf("please put the express you want to test:");
 scanf("%s",s);   //输入要分析的表达式
 while(s[strlen(s)-1]!='#')
 {
  printf("please input string again.# is the end of string/n");
  scanf("%s",s);
 }
 warehouse[q++]='#';
 warehouse[q++]='E';   //栈的初始化
 X=warehouse[--q];
 a=*(s+p++);
 while(1)
 {
  print1(warehouse,s+p-1,q);
  for(int j=0;j<8;j++)
   if(X==ensymbol[j])  //判读当前栈顶是不是终结符
   {
    b=1;
    break;
   }
  if(b)   //是终结符
  {
   if(X==a) //栈顶终结符是不是表达式要判读的终结符    是
   {
    if(X=='#') //判断终结符是不是结束符   是
    {
     if(X==a)
     {
      printf("success/n");
      return;  //该语句是该文法语句
     }
    }
    else        //不是终结符  把栈顶下移 和 表达式后移
    {
     a=*(s+p++);
     X=warehouse[--q];
     b=0;
    }
   }
   else     //栈顶表达式不是表达式要判断的终结符
   {
    printf("error/n");
    exit(1);  //不是该文法的语句
   }
  }
  else //当前栈顶是非终结符
  {
   int i=j=0;
   for(i;i<5;i++)
    if(X==nensymbol[i])  //查找当前栈顶非终极符产生判断终结符数组下标
     break;
   for(j;j<8;j++)
    if(a==ensymbol[j])
     break;
   if(j==8) //当前查找的字符不在终结符表里
   {
    printf("input is error .there is not a char in the ensymbol ./n");
    exit(1);
   }
   else     //在终结表里
   {
    int l;
    if(strcmp(forecast[i][j],nproduce)) //是否有产生式  没有
    {
     printf("forecast[%d][%d] is not a express grammar/n",i,j);
     exit(1);
    }
    else   //有产生式
    {
     l=strlen(forecast[i][j])-1;
     for(l;l>=0;l--)
     {
      if(*(forecast[i][j]+l)=='e')
       break;
      else
       warehouse[q++]=*(forecast[i][j]+l);
     }   //把数字的产生式放入栈中
     X=warehouse[--q]; //去出栈顶元素
    }
   }
  }
 }
}

如何修改使之更小

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值