题目来源:codeup contest ID:100000605 后缀式的求值可以用栈来解决,于是我们需要把输入的中缀表达式改成后缀。 注:计算器1.0不够成熟只能实现操作数在10以内的运算
至此,仅能实现10以内运算数的计算(类似10/30就会出错)
List item 改进计算函数 由于使用的是数组顺序栈,所以对于不同操作数的界限划分不够明显,于是想到用结构体栈 // An highlighted block struct infix_Num { int datas[MAX]; int top; };在上云实习的时候想了一下怎么修改,先贴个成品吧
// An highlighted block #include<cstdio> #define maxSize 50 int getpriority(char m)//获取运算符优先级 { switch(m) { case'+': case'-': return 1; break; case'*': case'/': return 2; break; } } int trans(char infix[], double s2[], int &top2)//中缀转后缀函数,注意返回值是int,一个小巧思 { double s1[maxSize];//存运算符的辅助栈 int top1 = -1; int i=0; int k=0;//用于记录后缀表达式的长度,并作为返回值返回 while(infix[i] !='\0') { if('0'<=infix[i]&&'9'>=infix[i]) { s2[++top2]=infix[i]-'0'; ++i;++k; while('0'<=infix[i]&&'9'>=infix[i]) { s2[top2]=infix[i]-'0'+s2[top2]*10; i++; } } else if (infix[i]=='(') { s1[++top1]='('-50; ++i; } else if(infix[i]=='+'|| infix[i]=='-'|| infix[i]=='*'|| infix[i]=='/') { if(top1==-1|| s1[top1]=='('-50|| getpriority(infix[i])>getpriority(s1[top1]+50)) { s1[++top1]=infix[i]-50; ++i; } else { s2[++top2]=s1[top1--]; ++k;} } else if(infix[i]==')') { while (s1[top1]!=('('-50)) { s2[++top2] = s1[top1--]; k++; } --top1;//出栈左括号 ++i; } } while (top1 !=-1) {s2[++top2] = s1[top1--];//出栈辅助栈剩余表达式 ++i;++k;} return k; } double op(double a,char Op,double b)//运算函数 { if(Op=='+') return a+b; if(Op=='-') return a-b; if(Op=='*') return a*b; if(Op=='/')//题目是非负整数 { if(b==0) { printf("error\n"); return 0; } else return a/b; } } double cal(double exp[],int k)//后缀式计算函数 { int i; double a,b,c; double stack[maxSize]; int top=-1; char Op; for(i=0;i<=k-1;++i)//k是长度,所以到k-1 { if(exp[i]<0) { Op=exp[i]+50; b=stack[top--]; a=stack[top--];//后进先出 c = op(a,Op,b) ; stack[++top]=c; } else stack[++top]=exp[i]; } return stack[top]; } int main() { char infix[maxSize]; gets(infix); double rinfix[maxSize]={0}; int top2=-1; int k =trans(infix,rinfix,top2); printf("%.2f",cal(rinfix,k)); return 0; }通过一系列改动实现了不借助结构体变量来进行带括号的四则运算(说白了有点偷懒不想改动太多哈哈哈,用结构体变量做起来肯定省心一些) 说说改动的几个关键点吧,顺便记录下思路 1、将输入的字符串存入一个double数组而不是通常的char数组 2、使用double数组是为了实现操作数大于十的运算,因为原来的程序前提是小于10(字符型) 3、为了区别double数组中的操作数与符号,符号入栈时将其减50(四则运算符号及括号ASCII均在40~50之间) 4、增加记录进栈元素个数的k以控制运算函数op的运算条件(现在想想好像用top2就行?) 在不断改进和完善的过程中更熟悉了顺序栈和调试的操作,要是愣找可能明年还在找bug吧2333 到此结束~