首页 诗词 字典 板报 句子 名言 友答 励志 学校 网站地图
当前位置: 首页 > 教程频道 > 开发语言 > C语言 >

会识别浮点数的简单语法分析程序(C语言实现)

2012-11-01 
能识别浮点数的简单语法分析程序(C语言实现)此语法分析程序的基本词法分析能够识别基本字、标识符、有符号整

能识别浮点数的简单语法分析程序(C语言实现)

此语法分析程序的基本词法分析能够识别基本字、标识符、有符号整数、有符号浮点数、运算符和界符)。

?

语法结构定义 ::= { +|-} ::= {*|/} ::=ID|num|()num::= ( +|-|ε ) 数字数字*(.数字数字* | ε)( e ( +|-|ε ) 数字数字*|ε)ID::=字母(字母|数字)*字母::=a|b|c…|z|A|B|C…|Z数字::=0|1|2…|9

?

词法分析程序需具备词法分析的功能:输入:所给文法的源程序字符串。(字符串以“#”号结束)输出:success 是文法正确句子;error 不是文法正确句子例如:输入 a+b*c# 输出success.

?

参考输入字符串:

?

(+123.456+-456.789e-120)*m2+(a++456)*c123

(+123.456+-456.789e-120)*m2+(a++456)*-123

(+123.456+-456.789e-120)*m2+(a++456)*-c123(标识符前加负号,输出error)

d+-11.7e-17

a+-149+49.7e+127+-m123(标识符前加负号,输出error)

a+-149+49.7e+127+m123

((a+b)*-14.79e+127)*379+m32

A+-128e-127-b21

A+-128e-127+-6

?

实现截图:
会识别浮点数的简单语法分析程序(C语言实现)


会识别浮点数的简单语法分析程序(C语言实现)

?

?

源代码:

?

?

#include<stdio.h>#include<string.h>int isError;char prog[80]; //存放所有输入字符   char token[8]; //存放词组   char ch; //单个字符     int syn,p,m,n;  //syn:种别编码   double sum;        int count;   int isSignal; //是否带正负号(0不带,1负号,2正号)int isDecimal; //是否是小数   double decimal;  //小数   int isExp;  //是否是指数   int index;  //指数幂   int isNegative; //是否带负号   double temp;   int temp2;int repeat; //是否连续出现+,-  void scanner();     char *rwtab[9]={"main","int","float","double","char","if","else","do","while"};void E();void T();void F();void scanner();void main(){p=0;count=0;isDecimal=0;index=0;repeat=0;printf("\n please input the source string:\n");do{ch=getchar();prog[p++]=ch;}while(ch!='#');p=0;isError=0;scanner();if((syn==20)||(syn==10)||(syn==26)) {E();}if((ch=='#')&&(isError==0))printf("success\n");elseprintf("error\n");}void E(){T();while((syn==22)||(syn==23)){scanner();T();}}void T(){F();while((syn==24)||(syn==25)){scanner();F();}}void F(){if((syn==20)||(syn==10))scanner();else if(syn==26){scanner();E();if(syn==27){scanner();}else isError=1;}else isError=1;}void scanner()   {       sum=0;       decimal=0;       m=0;         for(n=0;n<8;n++)           token[n]=NULL;       ch=prog[p++]; //从prog中读出一个字符到ch中       while(ch==' ')  //跳过空字符(无效输入)           ch=prog[p++];         if(((ch>='a')&&(ch<='z'))||((ch>='A')&&(ch<='Z'))) //ch是字母字符       {           while(((ch>='a')&&(ch<='z'))||((ch>='A')&&(ch<='Z'))||((ch>='0')&&(ch<='9')))           {               token[m++]=ch; //ch=>token               ch=prog[p++]; //读下一个字符           }           token[m++]='\0';           p--; //回退一格           syn=10; //标识符             //如果是"begin","if","then","while","do","end"标识符中的一个           for(n=0;n<9;n++)               if(strcmp(token,rwtab[n])==0)               {                   syn=n+1;                   break;               }       }        else if((ch>='0')&&(ch<='9'))       {   IsNum:   if(isSignal==1)   {   //token[m++]='-';   }        while((ch>='0')&&(ch<='9'))           {               sum=sum*10+ch-'0'; //ch中数字本身是当做字符存放的               ch=prog[p++];           }           if(ch=='.')           {               isDecimal=1;               ch=prog[p++];   count=0; //之前忘了清零,123.123+123.123#两个浮点数就无法识别            while((ch>='0')&&(ch<='9'))               {                   //pow(x,y)计算x的y次幂                   temp=(ch-'0')*pow(0.1,++count);                   decimal=decimal+temp;                   //AddToDec();                   ch=prog[p++];               }               sum=sum+decimal;           }           if(ch=='e'||ch=='E')           {               isExp=1;               ch=prog[p++];               if(ch=='-')               {                   isNegative=1;                   ch=prog[p++];               }               while((ch>='0')&&(ch<='9'))               {                   //指数                   index=index*10+ch-'0';                   ch=prog[p++];               }               //10的幂               //123e3代表123*10(3)               //sum=sum*pow(10,index);是错误的               if(isNegative)                   sum=sum*pow(0.1,index);               else                  sum=sum*pow(10,index);             }   if(isSignal==1){sum=-sum;isSignal=0;}        p--;           syn=20;       }         else switch(ch)       {           case '<':               m=0;               token[m++]=ch;               ch=prog[p++];                if(ch=='=')               {                   syn=35;                   token[m++]=ch;               }               else              {                   syn=34;                   p--;               }               break;             case '>':               m=0;               token[m++]=ch;               ch=prog[p++];               if(ch=='=')               {                   syn=33;                   token[m++]=ch;               }               else              {                   syn=32;                   p--;               }               break;             case '=':               m=0;               token[m++]=ch;               ch=prog[p++];               if(ch=='=')               {                   syn=36;                   token[m++]=ch;               }               else              {                   syn=21;                   p--;               }               break;     case '+':temp2=prog[p];token[m++]=ch;if((temp2>='0')&&(temp2<='9')&&(repeat==1)){isSignal=2;ch=prog[p++];repeat=0;goto IsNum;}if(((temp2=='+')||(temp2=='-'))&&(repeat==0))  //如果重复出现符号,才将后边的+,-视为正负号{repeat=1;//ch=prog[p++];}syn=22;break;case '-':temp2=prog[p];token[m++]=ch;if((temp2>='0')&&(temp2<='9')&&(repeat==1)){isSignal=1;ch=prog[p++]; //读“-”下一个字符repeat=0;goto IsNum;  //转到数字的识别}if(((temp2=='+')||(temp2=='-'))&&(repeat==0))  //如果重复出现符号,才将后边的+,-视为正负号{repeat=1;  //预言会重复//ch=prog[p++];  //读下一个字符}syn=23;break; /*        case '*':               syn=24;               token[m++]=ch;               break;*/case '*':temp2=prog[p];token[m++]=ch;if(temp2=='+'){isSignal=2;repeat=1;}else if(temp2=='-'){isSignal=1;repeat=1;}syn=24;break;        case '/':               syn=25;               token[m++]=ch;               break;    /*        case '(':               syn=26;               token[m++]=ch;               break;*/case '(':temp2=prog[p];token[m++]=ch;if(temp2=='+'){isSignal=2;repeat=1;}else if(temp2=='-'){isSignal=1;repeat=1;}syn=26;break;        case ')':               syn=27;               token[m++]=ch;               break;           case '{':               syn=28;               token[m++]=ch;               break;   case '}':               syn=29;               token[m++]=ch;               break;  case ',':               syn=30;               token[m++]=ch;               break;  case ';':               syn=31;               token[m++]=ch;               break;          case'#':               syn=0;               token[m++]=ch;               break;           default:               syn=-1;       }   }

热点排行