表达式计算 | ||||||
|
||||||
Description | ||||||
输入一个中缀表达式,要求输出计算的结果,保留到小数点后4为位。 表达式中的数均为非负数,可能为小数,不会出现-2,+2的情况,就是说不会有 1 + - 2、1 * -2、2*+2这样的情况。 数字为整数或者带小数的形式,如12、12.345. 符号定义如下: 加法 + ,减法 - ,乘法 * ,除法 / 。 括号 ( ) 。 优先级定义: 加法和减法优先级相同,乘法和除法的优先级相同,加法和减法的优先级比乘法和除法的优先级低。 遇到括号,则括号内的运算优先级高,以此类推。 |
||||||
Input | ||||||
有多组测试数据,测试数据组数不超过2000个。 每组占一行,不超过2000个字符。所含字符为空格,数字,"+", "-", "*", "/" ,"(",")",还有小数点"."。 保证每组测试数据均有解和数据的精度。 |
||||||
Output | ||||||
对于每组测试数据,输出一行,为表达式计算的结果,结果保留到小数点后2位。
|
||||||
Sample Input | ||||||
1 + 1 + 2 1 - 2.0 (1.0)+2-1*2 37- 89+ 80.295* (86.473)-67*42- (75.077)-5.144- 81.987+ 64.204* (11+ 22- (51-74.867)* (4.737)- (16.017)- 17)/ 23 |
||||||
Sample Output | ||||||
4.00 -1.00 1.00 4230.69 |
本题是HDU 1237的同类型题,稍难一点。思路相同。代码如下:
#include <cstdio> #include <cstring> #include <stack> using namespace std; stack<char> op; stack<double> num; char a[2005],aa[2005]; int oper(char o) { if(o=='+') return 1; if(o=='-') return 1; if(o=='*') return 2; if(o=='/') return 2; if(o=='(') return 3; if(o==')') return 4; return -1; } void hz(char *x) { int len=strlen(x); int k=0; memset(aa,' ',sizeof(aa)); for(int i=0;i<len;i++) { if(x[i]==' ') continue; aa[k++]=' '; while((x[i]>='0'&&x[i]<='9')||x[i]=='.') aa[k++]=x[i++]; if(oper(x[i])!=-1) { bool f=false; if(oper(x[i])==1) { while(!op.empty()e&&oper(op.top())!=3) { aa[k++]=op.top(); op.pop(); } } else if(oper(x[i])==2) { while(!op.empty()&&oper(op.top())==2) { aa[k++]=op.top(); op.pop(); } } else if(oper(x[i])==4) { while(oper(op.top())!=3) { aa[k++]=op.top(); op.pop(); } op.pop(); f=true; } if(!f) op.push(x[i]); } } while(!op.empty()) { aa[k++]=op.top(); op.pop(); } } double yunsuan(double x,char c,double y) { if(c=='+') return 1.0*x+y; if(c=='-') return 1.0*x-y; if(c=='*') return 1.0*x*y; if(c=='/') return 1.0*x/y; } double cal() { int len=strlen(aa); int k=0; double num1=0,num2=0,re; while(num.empty()==false) num.pop(); for(int i=0;i<len;i++) { bool flag=false; re=0; if(aa[i]==' ') continue; while(aa[i]>='0'&&aa[i]<='9') { re=re*10+aa[i]-'0'; i++; if(aa[i]=='.') { i++; int e=10; while(aa[i]>='0'&&aa[i]<='9') { re+=1.0*(aa[i]-'0')/e; i++; e*=10; } } flag=true; } if(flag==true) num.push(re); if(oper(aa[i])!=-1) { num1=num.top(); num.pop(); num2=num.top(); num.pop(); num.push(yunsuan(num2,aa[i],num1)); } } return num.top(); } int main() { while(gets(a)) { if(strcmp(a,"0")==0) break; hz(a); printf("%.2lf ",cal()); } return 0; }