表达式求值之栈的灵活运用
2013-07-31 16:27
197 查看
表达式求值
时间限制:3000 ms | 内存限制:65535 KB难度:4
描述 ACM队的mdd想做一个计算器,但是,他要做的不仅仅是一计算一个A+B的计算器,他想实现随便输入一个表达式都能求出它的值的计算器,现在请你帮助他来实现这个计算器吧。
比如输入:“1+2/4=”,程序就输出1.50(结果保留两位小数)
输入 第一行输入一个整数n,共有n组测试数据(n<10)。
每组测试数据只有一行,是一个长度不超过1000的字符串,表示这个运算式,每个运算式都是以“=”结束。这个表达式里只包含+-*/与小括号这几种符号。其中小括号可以嵌套使用。数据保证输入的操作数中不会出现负数。
数据保证除数不会为0 输出 每组都输出该组运算式的运算结果,输出结果保留两位小数。 样例输入
2 1.000+2/4= ((1+2)*5+1)/4=
样例输出
1.50 4.00
笔者认为关键点在于算术运算符优先级的比较,在本程序中我们把这个优先级事先存入一个二维表内;
再者就是栈的应用了,关键在于栈结构体的定义与栈基址的分配与赋值
源代码如下:
[code]#include<stdio.h> #include<string.h> #include<math.h> #include<stdlib.h> #define max 1010 typedef struct{ char *base; char *top; }Zhan1; typedef struct{ double *base1; double *top1; }Zhan2; char a1[max]; char GXB[10][10]={{'>','>','<','<','<','>','>'}, {'>','>','<','<','<','>','>'}, {'>','>','>','>','<','>','>'}, {'>','>','>','>','<','>','>'}, {'<','<','<','<','<','=','0'}, {'>','>','>','>','0','>','>'}, {'<','<','<','<','<','0','='}}; char fu[10]={'+','-','*','/','(',')','#'}; char Youxian(char a,char b){ int t,i,j; for(t=0;t<7;t++) if(fu[t]==a){i=t;break;} for(t=0;t<7;t++) if(fu[t]==b){j=t;break;} return GXB[i][j]; } void InitStack(Zhan1 &Fu,Zhan2 &Shu){ Fu.base=(char*)malloc(max*sizeof(char)); Fu.top=Fu.base; Shu.base1=(double*)malloc(max*sizeof(double)); Shu.top1=Shu.base1; } void Push(Zhan1 &Fu,char c){ *Fu.top++=c; } void Push1(Zhan2 &Shu,double t){ *Shu.top1++=t; } void Pop(Zhan1 &Fu,char &x){ x=*(--Fu.top); } void Pop1(Zhan2 &Shu,double &x){ x=*(--Shu.top1); } char Gettop(Zhan1 &Fu){ return *(Fu.top-1); } double Gettop1(Zhan2 &Shu){ return *(Shu.top1-1); } int In(char c){ int i; for(i=0;i<strlen(fu);i++) { if(c==fu[i])return 1; } return 0; } double Operate(double a,char e,double b){ double t; if(e=='+')return a+b; if(e=='-')return a-b; if(e=='*')return a*b; if(e=='/')return a/b; } void Maker(char *a1){ int len=strlen(a1); a1[len-1]='#'; }//Maker double Calculate(){ int i=0;//跟踪当前字符位序 char c,b1[1010],x,theta; int j; double t,a,b; Zhan1 Fu;Zhan2 Shu; memset(b1,'\0',sizeof(b1)); InitStack(Fu,Shu);//字符栈初始化 Push(Fu,'#'); c=a1[i++]; while(c!='#'||Gettop(Fu)!='#'){ if(!In(c)){ j=0; memset(b1,'\0',sizeof(b1)); while(!In(c)){ b1[j++]=c; c=a1[i++]; }//while t=atof(b1); Push1(Shu,atof(b1));//操作数进栈 }//if else switch(Youxian(Gettop(Fu),c)){ case'<': //栈顶元素优先权低 Push(Fu,c);c=a1[i++]; break; case'=': Pop(Fu,x);c=a1[i++]; break; case'>': Pop(Fu,theta); Pop1(Shu,b); Pop1(Shu,a); Push1(Shu,Operate(a,theta,b)); break; }//switch }//while return Gettop1(Shu); }//Calculate() int main() { int n; scanf("%d",&n); while(n--){ scanf("%s",a1); Maker(a1);//将输入的字符串去掉"="并在末端加上"#"字符 printf("%.2f\n",Calculate()); } Zhan1 Fu;Zhan2 Shu; InitStack(Fu,Shu);//字符栈初始化 Push(Fu,'#'); //system("pause"); return 0; }
[/code]
相关文章推荐
- 表达式求值(栈的运用)
- C++条件表达式的灵活运用
- 栈的运用! 表达式求值。
- 栈的运用(算数表达式求值的算符优先算法 十以内简单版)
- POJ 2106-Boolean Expressions,双栈运用类似表达式求值!
- 栈的运用-四则运算表达式求值
- 表达式求值(C实现,实现多括号,浮点数)---栈的实现以及运用。
- 九度+计算表达式模拟+scanf读取数据的灵活运用和运算级的处理
- 运用栈对算数表达式求值
- 栈的运用(中缀表达式转换为后缀表达式,并对后缀表达式求值。)
- NYOJ - 表达式求值(逆波兰式)
- 数据结构课程设计四则运算表达式求值(C语言版)
- lintcode-表达式求值-368
- swust 2551 表达式求值
- 表达式求值
- 将中缀表达式转化为后缀表达式进行加减乘除解析求值
- 表达式求值
- poj 1686 表达式求值判断
- 栈_对表达式求值
- C++实现任意表达式求值(栈)