-
题目描述
-
解题思路心得
最难写的一集
居然还有多位数和小数卡了好久,偷懒直接用了stack,感觉也不是这道题的重点吧…重点是字符串处理 多位数小数是直接用的字符串转换stod。整体思路其实不太难吧,理清楚后也写了注释了,反正我写出来了,而且感觉写的很漂亮,好耶!
-
代码
#include <stack>
#include <iostream>
#include <string>
#include <iomanip>
using namespace std;
int isops(char c)
{
switch (c)
{
case '+':
case '-':
case '*':
case '/':
case '(':
case ')':
case '=':
return 1;
default:
return 0;
}
}
double calculate(double x, double y, char c)
{
double res = 0;
switch (c)
{
case '+':
res = x + y;
break;
case '-':
res = x - y;
break;
case '*':
res = x * y;
break;
case '/':
res = x / y;
break;
default:
break;
}
return res;
}
void popCal(stack<char> &s, stack<double> &num)
{
double x, y;
char opt = s.top();
s.pop();
y = num.top();
num.pop();
x = num.top();
num.pop();
num.push(calculate(x, y, opt)); // 运算结果压入栈中
}
int level(char c)
{
int i = 0;
switch (c)
{
case '+':
case '-':
i = 1;
break;
case '*':
case '/':
i = 2;
break;
default:
break;
}
return i;
}
int main()
{
string str;
while (1)
{
cin >> str;
if (str[0] == '=')
{
break;
}
stack<char> ops;
stack<double> number;
for (int i = 0; str[i] != '='; )
{
// 如果是运算符
if (isops(str[i]))
{
// 第一个运算符和左括号直接进
if (ops.empty() || str[i] == '(')
{
ops.push(str[i]);
}
// 右括号算到左括号为止
else if (str[i] == ')')
{
while (ops.top() != '(')
{
popCal(ops, number);
}
ops.pop();
}
// 其他运算符情况
else
{
if (level(ops.top()) >= level(str[i]))
{
popCal(ops, number);
ops.push(str[i]);
}
else
{
ops.push(str[i]);
}
}
i++;
}
// 如果是数字
else
{
// 0-9正整数
if (isops(str[i + 1]))
{
number.push(str[i] - '0');
i++;
}
// 其他数
else if (!isops(str[i + 1]) && str[i + 1] != '=')
{
int index = i;
while (!isops(str[i]) && str[i]!='=')
{
i++;
}
string num=str.substr(index, i - index);
number.push(stod(num));
}
else
{
break;
}
}
}
// 要算完
while (!ops.empty())
{
popCal(ops, number);
}
cout <<fixed<<setprecision(2)<< number.top() << endl;
}
return 0;
}