这个怎么实现四则运算?
程序代码:#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define BUFSIZE 256
#define SHIFT(NUM) memcpy(&(stack[top].token),&curtoken,sizeof(TokenType));\
stack[++top].state=NUM;\
getnexttoken(word);\
break;
#define ERRORPROCESS fprintf(out,"Error line:%d\n",lineno);\
return;
typedef enum {NONE=-3, FEOF, ERROR,
/*词法符号*/
INTC,FLOATC,OPADD,OPSUB,OPMUL,OPDIV,LPAREN,RPAREN,LINE,ASSIGN,
/*文法的非终极符*/
S,E,T,P
} LexType;
static LexType lexstateflag[]={ERROR,INTC,FLOATC,ERROR,ERROR,ERROR,FLOATC,OPADD,
OPSUB,OPMUL,OPDIV,LPAREN,RPAREN,LINE,ASSIGN};
static FILE *in;
static FILE *out;
static char lexcurch=' ';
static char lexstack[BUFSIZE];
static int lexstacktop=-1;
static char lextryword[BUFSIZE];
static LexType lextryflag[BUFSIZE];
static int lexindex;
/*实现语法分析时使用的变量*/
typedef struct{
LexType type;
enum {INT,FLOAT} valuetype;
union{
int intv;
float floatv;
} value;
} TokenType;
static TokenType curtoken,buftoken={NONE};
static int lineno=1;
LexType lex(char *word)
{ int state;
lexindex=0;
state=0;
while(lexcurch==' '||lexcurch=='\t')
if (lexstacktop==-1)
lexcurch=fgetc(in);
else
lexcurch=lexstack[lexstacktop--];
while (1)
{
if (lexindex) lextryflag[lexindex-1]=lexstateflag[state];
switch (state){
case 0:
switch (lexcurch){
case '0': case '1': case '2': case '3': case '4':
case '5': case '6': case '7': case '8': case '9':
state=1;break;
case '.':
state=3;break;
case '+':
state=7;break;
case '-':
state=8;break;
case '*':
state=9;break;
case '/':
state=10;break;
case '(':
state=11;break;
case ')':
state=12;break;
case '\n':
state=13;break;
case '=':
state=14;break;
default:
state=-1;break;
} ;
break;
case 1:
switch (lexcurch){
case '0': case '1': case '2': case '3': case '4':
case '5': case '6': case '7': case '8': case '9':
state=1;break;
case '.':
state=2;break;
case 'E': case 'e':
state=4;break;
default:
state=-1;break;
} ;
break;
case 2:
switch (lexcurch){
case '0': case '1': case '2': case '3': case '4':
case '5': case '6': case '7': case '8': case '9':
state=2;break;
case 'E': case 'e':
state=4;break;
default:
state=-1;break;
} ;
break;
case 3:
switch (lexcurch){
case '0': case '1': case '2': case '3': case '4':
case '5': case '6': case '7': case '8': case '9':
state=2;break;
default:
state=-1;break;
} ;
break;
case 4:
switch (lexcurch){
case '0': case '1': case '2': case '3': case '4':
case '5': case '6': case '7': case '8': case '9':
state=6;break;
case '+': case '-':
state=5;break;
default:
state=-1;break;
} ;
break;
case 5:
switch (lexcurch){
case '0': case '1': case '2': case '3': case '4':
case '5': case '6': case '7': case '8': case '9':
state=6;break;
default:
state=-1;break;
} ;
break;
case 6:
switch (lexcurch){
case '0': case '1': case '2': case '3': case '4':
case '5': case '6': case '7': case '8': case '9':
state=6;break;
default:
state=-1;break;
} ;
break;
case 7:
state=-1;break;
case 8:
state=-1;break;
case 9:
state=-1;break;
case 10:
state=-1;break;
case 11:
state=-1;break;
case 12:
state=-1;break;
case 13:
state=-1;break;
case 14:
state=-1;break;
default:
state=-1;break;
}
if (state==-1)
break;
lextryword[lexindex++]=lexcurch;/*maybe overflow*/
if (lexstacktop==-1)
lexcurch=fgetc(in);
else
lexcurch=lexstack[lexstacktop--];
}
if (lexindex==0&&lexcurch==EOF)
return FEOF;
lextryword[lexindex]=lexcurch;
lextryflag[lexindex]=ERROR;
while (lexindex>0 && lextryflag[lexindex]==ERROR)
lexstack[++lexstacktop]=lextryword[lexindex--];/*maybe overflow*/
lextryword[lexindex+1]=0;
strcpy(word,lextryword);
if (lexstacktop==-1)
lexcurch=fgetc(in);
else
lexcurch=lexstack[lexstacktop--];
return lextryflag[lexindex];
}
void getnexttoken(char *word)
{
if (buftoken.type==NONE)
do {
curtoken.type=lex(word);
if (curtoken.type==INTC){
curtoken.valuetype=INT;
curtoken.value.intv=atoi(word);
}
if (curtoken.type==FLOATC){
curtoken.valuetype=FLOAT;
curtoken.value.floatv=atof(word);
}
if (curtoken.type==ERROR)
fprintf(out,"Error line:%d %s\n",lineno,word);
if (curtoken.type==LINE)
lineno++;
}while(curtoken.type==ERROR||curtoken.type==LINE);
else {
memcpy(&curtoken,&buftoken,sizeof(TokenType));
buftoken.type=NONE;
}
}
void parse(void)
{
struct{
int state;
TokenType token;
} stack[BUFSIZE];
int top=-1;
char word[80];
float ta,tb;
stack[++top].state=0;
getnexttoken(word);
while (1){
switch(stack[top].state){
case 0:
switch(curtoken.type) {
case E: SHIFT(1)
case T: SHIFT(2)
case P: SHIFT(3)
case INTC: SHIFT(4)
case FLOATC: SHIFT(5)
case LPAREN: SHIFT(6)
default: ERRORPROCESS
}
break;
case 1:
switch(curtoken.type) {
case ASSIGN: /* R1 */
memcpy(&buftoken,&curtoken,sizeof(TokenType));
memcpy(&curtoken,&(stack[top-1].token),sizeof(TokenType));
curtoken.type=S;
top=top-1;
/* ACCEPT */
if (curtoken.valuetype==INT)
fprintf(out, "%d\n",curtoken.value.intv);
if (curtoken.valuetype==FLOAT)
fprintf(out, "%f\n",curtoken.value.floatv);
return;
case OPADD: SHIFT(7)
case OPSUB: SHIFT(8)
default: ERRORPROCESS
}
break;
/* need code here */
case 15:
switch(curtoken.type) {
case ASSIGN:
case OPADD:
case OPSUB:
case RPAREN:
case OPMUL:
case OPDIV: /* R7 */
memcpy(&buftoken,&curtoken,sizeof(TokenType));
curtoken.type=T;
if ( stack[top-3].token.valuetype==INT &&
stack[top-1].token.valuetype==INT &&
(stack[top-3].token.value.intv %
stack[top-1].token.value.intv==0) ){
curtoken.valuetype=INT;
curtoken.value.intv=stack[top-3].token.value.intv /
stack[top-1].token.value.intv;
}else{
curtoken.valuetype=FLOAT;
if (stack[top-3].token.valuetype==INT)
ta=(float)(stack[top-3].token.value.intv);
else ta=stack[top-3].token.value.floatv;
if (stack[top-1].token.valuetype==INT)
tb=(float)(stack[top-1].token.value.intv);
else tb=stack[top-1].token.value.floatv;
curtoken.value.floatv=ta/tb;
}
top=top-3;
break;
default: ERRORPROCESS
}
break;
case 16:
switch(curtoken.type) {
case ASSIGN:
case OPADD:
case OPSUB:
case RPAREN:
case OPMUL:
case OPDIV: /* R10 */
memcpy(&buftoken,&curtoken,sizeof(TokenType));
memcpy(&curtoken,&(stack[top-2].token),sizeof(TokenType));
curtoken.type=P;
top=top-3;
break;
default: ERRORPROCESS
}
break;
default:
ERRORPROCESS
}
}
}
int main()
{
in=stdin;
out=stdout;
parse();
getchar();getchar();
return 0;
}







