NYOJ_128 前缀式计算

来源:互联网 发布:创业公司取名 知乎 编辑:程序博客网 时间:2024/05/11 06:11
描述

先说明一下什么是中缀式:

如2+(3+4)*5这种我们最常见的式子就是中缀式。

而把中缀式按运算顺序加上括号就是:(2+((3+4)*5))

然后把运算符写到括号前面就是+(2 *( +(3 4) 5) )

把括号去掉就是:+ 2 * + 3 4 5

最后这个式子就是该表达式的前缀表示。

给你一个前缀表达式,请你计算出该前缀式的值。

比如:

+ 2 * + 3 4 5的值就是 37

输入
有多组测试数据,每组测试数据占一行,任意两个操作符之间,任意两个操作数之间,操作数与操作符之间都有一个空格。输入的两个操作数可能是小数,数据保证输入的数都是正数,并且都小于10,操作数数目不超过500。
以EOF为输入结束的标志。
输出
对每组数据,输出该前缀表达式的值。输出结果保留两位小数。
样例输入
+ 2 * + 3 4 5+ 5.1 / 3 7
样例输出
37.005.53

方法一:    

使用栈的结构,从前向后依次扫描,当扫描到一个数字时,看栈顶的元素是否是一个数字,若是数字,则依次弹出两个元素,进行计算出结果,此时注意不要直接压栈,要看此时栈顶的元素是否是数字,若是则继续运算。直到栈顶的元素不是数字,才将计算的结果压到栈中。


代码:

#include<cstdlib>
#include<string.h>
#include<iostream>
#include<cmath>
#include<cstring>
#include<algorithm>
#include<iomanip>
#include<ctime>
#include<cstdio>
#include<stack>
#include<map>
#include<queue>
#include<vector>
#include<cctype>
using namespace std;

#define maxn 5090
struct Node
{
    double dig;
    char oper;
}sta[maxn];

char buf[maxn];

double calc(double a,double b,char c)
{
    if(c=='+')   return a+b;
    if(c=='-')   return a-b;
    if(c=='*')   return a*b;
    return a/b;    
}

int main()
{
    double val;
    int wid;
    while(gets(buf))
    {
        for(int i=0 , id=0 ; buf[i]!='\0' ; ++i)
        {
            if(buf[i]==' ')   continue;
            
            if(isdigit(buf[i]) || buf[i]=='.')
            {
                sscanf(buf+i,"%lf%n", &val,&wid);
                while(id && !sta[id-1].oper)
                {
                    val = calc(sta[id-1].dig,val,sta[id-2].oper);
                    id-=2;                    
                }        
                sta[id].dig = val;
                sta[id++].oper = 0;
                i+=wid-1;
            }
            else
                sta[id++].oper = buf[i];            
        }
        printf("%.2lf\n",sta[0].dig);
    }    
    return 0;
}


方法二:(神用递归啊)

string res;

double temp;

sscanf(res.c_str(), "%lf" , &temp);    //将string类型的数据转化成char类型的数组

代码:

#include<cstdlib>
#include<string.h>
#include<iostream>
#include<cmath>
#include<cstring>
#include<algorithm>
#include<iomanip>
#include<ctime>
#include<cstdio>
#include<stack>
#include<map>
#include<queue>
#include<vector>
#include<cctype>
using namespace std;

int i;
string str;
double temp;

double ac()
{
    ++i;
    if(str[i]==' ') ++i;
    if(isdigit(str[i]))
    {
        string res;
        while(i!=str.size() && str[i]!=' ')
        {
            res +=str[i++];
        }
        sscanf(res.c_str(), "%lf" , &temp);
        return temp;        
    }
    if(str[i]=='+')
        return ac()+ac();
    if(str[i]=='-')
        return ac()-ac();
    if(str[i]=='*')
        return ac()*ac();
    if(str[i]=='/')
        return ac()/ac();    
}

int main()
{    
    while(getline(cin,str))
    {
        i=-1;
        printf("%.2lf\n",ac());
    }    
    return 0;
}

1 0
原创粉丝点击