最初接触此类的题目,是只涉及到的加减乘除四则运算,没有符号的操作,因为在一次笔试中遇到了有括号的情况,抱着遇到问题一定要去解决的态度,笔试结束后尝试将这道题目进行还原。
这里的思想主要是用到了栈,分为两个栈,一个栈存放数字,另外一个栈存放运算符和括号
#include <cstdio>
#include <stack>
using namespace std;
char str[200];
int mat[][5]={
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<double> in;
stack<int> op;
void getOp(bool &reto,int &retn,int &i)
{
if(i==0&&op.empty()==true)
{
reto = true;
retn = 0;
return ;
}
if(str[i]==0)
{
reto = true;
retn = 0;
return ;
}
if(str[i]>='0'&&str[i]<='9')
{
reto = false;
retn = 0;
while(str[i]>='0'&&str[i]<='9')
{
retn = retn*10 + (str[i++] -'0');
}
return ;
}
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;
}
else if(str[i]=='('){
retn = 5;
}
else if(str[i]==')'){
retn=6;
}
i++;
return ;
}
}
int main()
{
bool flag = false;
while(gets(str))
{
if(str[0]=='0'&&str[1]==0) break;
bool retop;int retnum;
int idx=0;
while(!op.empty()) op.pop();
while(!in.empty()) in.pop();
while(true)
{
getOp(retop,retnum,idx);
if(retop==false)
{
in.push(retnum);
}
else
{
double tmp;
//这里分为三种情况
//1)符号栈是空的,需要加入标记位0,说明是运算的开始
//2)当前的符号属于四则运算的范畴,且当前符号的优先级大于符号栈顶的优先级
//3)当前的符号为'('左括号,无脑入栈
if(op.empty()==true||(mat[retnum][op.top()]==1&&retnum<=4)||retnum==5)
{
op.push(retnum);
}
else if(retnum<=4&&mat[retnum][op.top()]==0)
{
while(mat[retnum][op.top()]==0)
{
int ret = op.top();
op.pop();
int b = in.top();
in.pop();
int a = in.top();
in.pop();
if(ret==1) tmp=a+b;
else if(ret==2) tmp=a-b;
else if(ret==3) tmp=a*b;
else
{
if(b!=0)
tmp=a/b;
else
{
flag=true;
break;
}
}
in.push(tmp);
}
op.push(retnum);
if(flag)
{
break;
}
}else if(retnum==6){
//当前的符号是')'右括号,需要找他的好基友左括号,找到为止
while(op.top()!=5){
int ret = op.top();
op.pop();
int b = in.top();
in.pop();
int a = in.top();
in.pop();
if(ret==1) tmp=a+b;
else if(ret==2) tmp=a-b;
else if(ret==3) tmp=a*b;
else
{
if(b!=0)
tmp=a/b;
else
{
flag=true;
break;
}
}
in.push(tmp);
}
op.pop();
}
}
if(op.size()==2&&op.top()==0) break;
}
if(flag==false)
printf("%.0f\n",in.top());
else
break;
}
return 0;
}