NYOJ 35 表达式求值(一)

2014-11-24 03:33:36 · 作者: · 浏览: 3
本题是求算数表达式的值。操作数是大于等于的实数,操作符有 + ,- ,*,/,()
只要开两个栈,一个记录操作符,一个记录后缀表达式。
即:把原始的中缀表达式转换成后缀表达式(逆波兰式),然后进行计算。
前缀和后缀表示法有三项公共特征:
操作数的顺序与等价的中缀表达式中操作数的顺序一致
不需要括号
操作符的优先级不相关
中缀转化为后缀算法:
a. 得到一操作符或操作数;
b. 若输入为操作数,则输出到数组,转a;
c. 若输入为‘(’,压栈,转a;
d. 若输入为‘)’,栈顶出栈,输出到数组,直至栈顶为‘(’,不输出到数组(抛弃),转a;
e. 若输入为操作符,
若栈空或栈顶为‘(’或操作符.忧先级大于栈顶操作符,压栈,转a
若操作符优先级小于栈顶操作符,则出栈,输出至数组,转e;
d. 若输入结束,出栈,输出到数组,直至栈空。
[cpp]
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
using namespace std;
int priority[100];
//初始化操作符优先级
void initPri()
{
priority['('] = 1;
priority['+'] = 2;
priority['-'] = 2;
priority['*'] = 3;
priority['/'] = 3;
}
//a是符号栈顶,b是当前判断符号
//a>=b,返回true;a
bool judgeOpePri(char a,char b)
{
return priority[a] >= priority[b] true : false;
}
//两个参数:中缀表达式,生成的后缀表达式
void convert(string infixExp,stack &postfixExp)
{
//运算符栈
stack opS;
//临时操作数
string digitTemp;
//临时操作符
string operTemp;
int len = infixExp.length();
bool hasDigit = false;
//过滤掉'='
for(int i=0; i
{
//如果是操作数的一部分
while((isdigit(infixExp[i]) || infixExp[i] == '.') && i
{
hasDigit = true;
digitTemp.push_back(infixExp[i]);
i++;
}
if(hasDigit == true)
{
postfixExp.push(digitTemp);
digitTemp = "";
hasDigit = false;
}
else
{
//如果操作符栈是空的,就入栈
if(opS.empty())
{
opS.push(infixExp[i]);
i++;
}
//注意对于'('同等优先级是不起作用的
else if(infixExp[i] == '(')
{
opS.push(infixExp[i]);
i++;
}
//弹出"()"之内的所有运算符
else if(infixExp[i] == ')')
{
while(!opS.empty())
{
char c = opS.top();
operTemp = "";
operTemp.push_back(c);
opS.pop();
if(c == '(')
{
break;
}
else
{
postfixExp.push(operTemp);
}
}
i++;
}
//操作符栈顶的优先级大
else if(judgeOpePri(opS.top(),infixExp[i]) == true)
{
char c = opS.top();
operTemp = "";
operTemp.push_back(c);
opS.pop();
postfixExp.push(operTemp);
//注意此时不要i++,因为还要继续比较
}
//操作符栈顶的优先级小
else
{
opS.push(infixExp[i]);
i++;
}
}
}
//清空符号栈
while(!opS.empty())
{
char c = opS.top();
operTemp = "";
operTemp.push_back(c);
opS.pop();
postfixExp.push(operTemp);
}
}
double answerQ(stack &postfixExp)
{
stack couterFix;
stack resultSta;
while(!postfixExp.empty())
{
couterFix.push(postfixExp.top());
postfixExp.pop();
}
double a,b;
while(!couterFix.empty())
{
st