zj@zj:~/C_parm/data_s$ cat expr.c #include <stdio.h> #include <stdlib.h> #include <string.h> #define MAXSIZE 4000; typedef struct { char data[10]; int top;//头地址 int base;//基地址 int length;//长度 }Stack; void init(Stack *st)//初始化栈 { st->base=0; st->top=0; st->length=0; } int isEmpty(Stack *st) { int n=0,top,base; top =st->top; base =st->base; if(top==base) { return 1; } return n; } int isFull(Stack *st) { int n=0,top,base; top =st->top; if(top>=4000) { return 1; } return n; } char getTop(Stack *st)// 返回top值,不改变栈的结构 { char n; if(isEmpty(st)) { printf("栈为空/n"); return 0; } int positon= st->top-1; n= st->data[positon];//取出数据; return n; } char pop(Stack *st)// 出栈,返回 { char n; if(isEmpty(st)) { printf("栈为空/n"); return 0; } int positon= st->top-1; n= st->data[positon];//取出数据; st->top--; st->length--; st->data[positon]='/0';//消除数据 return n; } void push(char n,Stack *st)//入栈 { int positon ; if(isFull(st)) { printf("栈满/n"); } else { positon= st->top;//获取位置 st->data[positon]=n;//存入数据 st->top++;//改变位置 } } void show(Stack *m1)//输出栈中的数据 { int top,base; top=m1->top; base=m1->base; while(top>base) { printf("%c,",m1->data[--top]); } printf("/n"); } int isOperate(char temp)//是否是操作符 { if(temp=='+'||temp=='-'||temp=='*'||temp=='/'||temp=='('||temp==')'||temp=='#') { return 1; } return 0; } int isValue(char temp)//是否是数值 { if(temp>='0'&&temp<='9')// { return 1; } else { return 0; } } int isAvail(char temp)//是否有效字符 { if(isOperate(temp)||isValue(temp))//如果temp既不是操作符和数值的话,则它是非法的 { return 1; } return 0; } int detect(char temp)//搜索矩阵位置 { int i=0; char oper[7]={'+','-','*','/','(',')','#'}; for(i=0;i<7;i++) { if(temp==oper[i]) { return i; } } } char Priority(char temp,char optr)//判断优先级 { /**//* + - * / ( ) # 1 2 3 4 5 6 7 + 1 < < < < > > > - 2 < < < < > > > * 3 > > < < > > > / 4 > > < < > > > ( 5 > > > > > = 0 ) 6 < < < < = 0 > # 7 < < < < > 0 = */ int row ,col; char priority[7][7]={/**//* + - * / ( ) # */ {'<','<','<','<','>','>','>'}, {'<','<','<','<','>','>','>'}, {'>','>','<','<','>','>','>'}, {'>','>','<','<','>','>','>'}, {'>','>','>','>','>','=','>'}, {'<','<','<','<','=','0','>'}, {'<','<','<','<','>','<','='}, }; row = detect(temp);//找出对应的矩阵下标; col = detect(optr); // printf("%d,%d",row,col); //优先级存储在一个7x7的矩阵中,对应关系上图; return priority[row][col]; } char evaluate(int a,int b,char oper) { switch(oper) { case '+': return a+b+'0'; case '-': return a-b+'0'; case '*': return a*b+'0'; case '/': return a/b+'0'; default : return 0+'0'; } } int calculateExpress(char *express)//计算表达式 { int result=0; int a,b; // char oper,result; Stack OPTR,OPND;//OPTR存储操作符,OPND操作数值 init(&OPTR); init(&OPND); push('#',&OPTR);//默认第一个位'#' ////////////////////-算法-//////////////////////////// while(*express!='/0') { char temp; temp= *(express); printf("---------------------------------/n"); printf("当前的符号为%c/n",temp); if(isAvail(temp))//是否是有效字符 { if(isOperate(temp) )//输入的是操作符 { char oper,result; char optr = getTop(&OPTR);//栈中top位的操作符 printf("栈顶操作符位:%c/n",optr); char prior = Priority(temp,optr);//判断优先级 switch(prior) { case '>': push(temp,&OPTR); printf("将符号位%c入栈/n",temp); express++; break; case '<': //int a,b; //char oper,result; a=pop(&OPND)-'0';//存在栈中的都是char字符 b=pop(&OPND)-'0'; oper=pop(&OPTR); result=evaluate(b,a,oper);//出栈一个操作符,计算结果 //printf("%d",result-'0'); push(result,&OPND);//结果入OPND printf("%d%c%d结果为:%d/n",b,oper,a,result-'0'); break; case '=': //消除括号 pop(&OPTR); printf("消除括号/n"); express++; break; } } if(isValue(temp))//输入的是数值 { push(temp,&OPND);//将数值位入栈; express++; printf("将数值%c压入栈/n",temp); //show(&OPND); } } else //表达式中有非法字符 { printf("表达式中有非法字符/n"); exit(-1);//退出程序 } } // show(&OPND); // show(&OPTR); return getTop(&OPND)-'0'; } void inputExpress(char *express)//输入表达式 { int length=0; printf("请输入一个表达式:"); scanf("%s",express); int len =strlen(express); express[len]='#';//表达式最后一位默认为'#'; express[len+1]='/0'; } void output(char *express,int result)//输出表达式 { int i=0; printf("----------------------------------------/n表达式:"); while(express[i]!='#') { printf("%c",express[i]); i++; } printf("=%d/n",result); } int main() { char express[100];//表达式 int result =0; inputExpress(express);//输入表达式 result = calculateExpress(express);//计算表达式; output(express,result); //输出表达式 //、、、、、、、、、、、、、测试优先级。 /**//* char m='7' ; m=Priority('+','*'); printf("优先级为%c",m); int m=evaluate(5,6,'m'); printf("%d",m); */ return 0; } zj@zj:~/C_parm/data_s$ ./expr 请输入一个表达式:2*3+(4+8)/3-2 --------------------------------- 当前的符号为2 将数值2压入栈 --------------------------------- 当前的符号为* 栈顶操作符位:# 将符号位*入栈 --------------------------------- 当前的符号为3 将数值3压入栈 --------------------------------- 当前的符号为+ 栈顶操作符位:* 2*3结果为:6 --------------------------------- 当前的符号为+ 栈顶操作符位:# 将符号位+入栈 --------------------------------- 当前的符号为( 栈顶操作符位:+ 将符号位(入栈 --------------------------------- 当前的符号为4 将数值4压入栈 --------------------------------- 当前的符号为+ 栈顶操作符位:( 将符号位+入栈 --------------------------------- 当前的符号为8 将数值8压入栈 --------------------------------- 当前的符号为) 栈顶操作符位:+ 4+8结果为:12 --------------------------------- 当前的符号为) 栈顶操作符位:( 消除括号 --------------------------------- 当前的符号为/ 栈顶操作符位:+ 将符号位/入栈 --------------------------------- 当前的符号为3 将数值3压入栈 --------------------------------- 当前的符号为- 栈顶操作符位:/ 12/3结果为:4 --------------------------------- 当前的符号为- 栈顶操作符位:+ 6+4结果为:10 --------------------------------- 当前的符号为- 栈顶操作符位:# 将符号位-入栈 --------------------------------- 当前的符号为2 将数值2压入栈 --------------------------------- 当前的符号为# 栈顶操作符位:- 10-2结果为:8 --------------------------------- 当前的符号为# 栈顶操作符位:# 消除括号 ---------------------------------------- 表达式:2*3+(4+8)/3-2=8 |