zoukankan      html  css  js  c++  java
  • [STL][stack]简单计算器

    Problem Description
    读入一个只包含 +, -, *, / 的非负整数计算表达式,计算该表达式的值。
     
    Input
    测试输入包含若干测试用例,每个测试用例占一行,每行不超过200个字符,整数和运算符之间用一个空格分隔。没有非法表达式。当一行中只有0时输入结束,相应的结果不要输出。
     
    Output
    对每个测试用例输出1行,即该表达式的值,精确到小数点后2位。
     
    Sample Input
    1 + 2 4 + 2 * 5 - 7 / 11 0
     
    Sample Output
    3.00 13.36

     思路:栈的应用——表达式求值;利用栈将中缀表达式转后缀表达式(转的同时计算后缀表达式的值)

     参考:https://blog.csdn.net/u014532901/article/details/52524624#代码示例

    AC代码:

    //表达式求值
    #include <iostream> #include<cstdio> #include<stack> #include<cstring> using namespace std; char s[1010]; int getnum(int i,int j){ if(i>j) return -1; int ret=0; for(int k=i;k<=j;k++){ if(s[k]!=' ') ret=ret*10+(s[k]-'0'); } return ret; } int cmp(char a,char b){//若a的优先级大于等于b,返回1,否则返回-1 if(a=='*'||a=='/') return 1; else if(a=='+'||a=='-'){ if(b=='*'||b=='/') return -1; else return 1; } else{ if(b=='#') return 1; else return -1; } } double cal(double a,double b,char c){ if(c=='+') return a+b; if(c=='-') return a-b; if(c=='*') return a*b; if(c=='/') return a*1.0/(b*1.0); return 0; } int main() { while(gets(s)){ int len=strlen(s); if(len==1&&s[0]=='0') break; s[len]='#';//保证了计算结束后操作符栈中只剩一个'#' stack<double> stk_digits; stack<char> stk_operator; for(int i=0,j=0;i<=len;){ if(s[i]==' '||(s[i]>='0'&&s[i]<='9')) i++; else{ int num=getnum(j,i-1);//将s[j~i-1]这一段字符串转为数值 if(num!=-1) {stk_digits.push(num); j=i+1;} if(stk_operator.empty()) {stk_operator.push(s[i]); i++;} else{ if(cmp(stk_operator.top(),s[i])==1) { double tmp2=stk_digits.top(); stk_digits.pop(); double tmp1=stk_digits.top(); stk_digits.pop(); stk_digits.push(cal(tmp1,tmp2,stk_operator.top())); stk_operator.pop(); } else {stk_operator.push(s[i]); i++;} } } } printf("%.2f ",stk_digits.top()); } return 0; }

    对于此题,也可以用不转后缀表达式的方法:

    #include <iostream>
    #include<cstdio>
    #include<algorithm>
    #include<cstring>
    using namespace std;
    
    int main()
    {
        double tmp;
        double num[1010];//因式
        while(scanf("%lf",&tmp)!=EOF){
            int cnt=0;
            char c=getchar();
            if(tmp==0&&c=='
    ') break;
            memset(num,0,sizeof(num));
            num[++cnt]=tmp;
            if(c=='
    ') {printf("%.2f
    ",num[cnt]); continue;}
            char op; double x;
            while(1){
                scanf("%c%lf",&op,&x);
                if(op=='*') num[cnt]*=x;
                if(op=='/') num[cnt]/=(x*1.0);
                if(op=='+') num[++cnt]=x;
                if(op=='-') num[++cnt]=-x;
                if(getchar()=='
    ') break;
            }
            double ans=0;
            for(int i=1;i<=cnt;i++) ans+=num[i];
            printf("%.2f
    ",ans);
        }
        return 0;
    }
    转载请注明出处:https://www.cnblogs.com/lllxq/
  • 相关阅读:
    span设置宽和高当没有内容的时候也可撑开
    span设置宽和高当没有内容的时候也可以撑开
    块级元素以及内联元素大总结
    内存泄露问题
    Sqlcompletefree
    运用SET ANSI_PADDING OFF创建某个字段为自增列的表,以及插入数据
    Sql Server中通配符
    sql server 2008查询窗口怎么显示行数
    sql server 2008语句中的go有什么用?
    SQL Server 2008 R2[ALTER]列属性修改
  • 原文地址:https://www.cnblogs.com/lllxq/p/9064784.html
Copyright © 2011-2022 走看看