1101.表达式求值(难)

题目描述:

对于一个不存在括号的表达式进行计算

输入:

存在多种数据,每组数据一行,表达式不存在空格

输出:

输出结果

样例输入:
6/2+3+3*4
样例输出:
18


#include<stack>
#include<stdio.h>
using namespace std;
char str[220];//保存表达式字符串 
int mat[][5]={//优先级矩阵,mat[i][j]=1,代表i号运算符优先级大于j号运算符 
    1,0,0,0,0,
    1,0,0,0,0,
    1,0,0,0,0,
    1,1,1,0,0,
    1,1,1,0,0,
}; 
stack<int>op;//运算符栈
stack<double>in;//数字栈
void getOp(bool &reto,int&retn,int&i){
    //获得表达式中下一个元素,若函数运行结束时,引用变量reto为true,则表示该元素为一个运算符,其编号保存在retn中;
    //否则,表示该元素为一个数字,其值保存在retn中。引用变量i表示遍历到的字符串下标
    if(i==0&&op.empty()==true)//若此时遍历字符串第一个字符,且运算符栈为空,我们人为添加标记为0的标记字符 
    {
        reto=true;//为运算符, 
        retn=0;//编号为0 
        return;
    } 
    if(str[i]=='\0'){//若此时遍历字符为空字符,则表示字符串已经被遍历完 
        reto=true;//返回为运算符 
        retn=0;//编号为0 
        return; 
    } 
    if(str[i]>='0'&&str[i]<='9')//若当前字符为数字 
    {
        reto=false;//返回为数字 
    }
    else{
        reto=true;//返回为运算符
        if(str[i]=='+'){
            retn=1;
        }
        else if(str[i]=='-'){
            retn=2;
        }
        else if(str[i]=='*'){
            retn=3;
        }
        else if(str[i]=='/'){
            retn=4;
        }
        i+=1;//i递增,跳过该运算符和该运算字符后的空格 
        return;
    }
    retn=0;//返回结果为数字
    for(;str[i]>='0'&&str[i]<='9'&&str[i]!=0;i++)
    {
        retn*=10;
        retn+=str[i]-'0';
    }//计算该数字的值 
    //if(str[i]==' ')//若其后字符为空格,则表示字符串未被遍历完 
    //{
    //  ++i;//i递增,跳过该空格 
    //} 
    return; 
} 
int main()
{
    while(scanf("%s",str)!=EOF)
    {
        bool retop;int retnum;//定义函数所需的变量
        int idx=0;//定义遍历到的字符串下标,初始值为0
        while(!op.empty())op.pop();
        while(!in.empty())in.pop();//清空数字栈和运算符栈
        while(true)//循环遍历表达式字符串 
        {
            getOp(retop,retnum,idx);//获取表达式中下一个元素 
            if(retop==false){//若该元素为数字 
                in.push((double)retnum);//将其压入数字栈 
            } 
            else{
                double tmp;
                if(op.empty()==true||mat[retnum][op.top()]==1){//若运算符堆栈为空或者遍历到的运算符优先级大于栈顶运算符,将该运算符压入运算符堆栈 
                    op.push(retnum);
                }
                else{
                    while(mat[retnum][op.top()]==0)//只要当前运算符优先级小于栈顶元素运算符,则重复循环 
                    {
                        int ret=op.top();//保存栈顶运算符
                        op.pop();//弹出
                        double b=in.top();
                        in.pop();
                        double a=in.top();
                        in.pop();//从数字堆栈栈顶弹出两个数字,依次保存在遍历a,b中
                        if(ret==1)tmp=a+b;
                        else if(ret==2)tmp=a-b;
                        else if(ret==3)tmp=a*b;
                        else tmp=a/b;
                        in.push(tmp); 
                    }
                    op.push(retnum);//将当前运算符压入运算符堆栈 
                }
            }
            if(op.size()==2&&op.top()==0)break; 
        }
        printf("%d\n",(int)in.top());
          
    }
    return 0;
}

 

posted @ 2018-10-02 10:29  bernieloveslife  阅读(266)  评论(0编辑  收藏  举报