结构与算法 7-20 表达式转换 (测试点分析)

7-20 表达式转换 (25 分)

算术表达式有前缀表示法、中缀表示法和后缀表示法等形式。日常使用的算术表达式是采用中缀表示法,即二元运算符位于两个运算数中间。请设计程序将中缀表达式转换为后缀表达式。

输入格式:

输入在一行中给出不含空格的中缀表达式,可包含+-*\以及左右括号(),表达式不超过20个字符。

输出格式:

在一行中输出转换后的后缀表达式,要求不同对象(运算数、运算符号)之间以空格分隔,但结尾不得有多余空格。

输入样例:

2+3*(7-4)+8/4

输出样例:

2 3 7 4 - * + 8 4 / +

需要支持多位数(包含小数)的加减乘除及优先级运算

另外需考虑数字带有符号(+,-)

#include <iostream>
#include <vector>
#include <map>
#include <stack>
using namespace std;
map<char, int> priority = {	{'*',3},{'/',3},{'+',2},{'-',2},{'(',1}};
vector<string> trans(string m_exp) {
	vector<string> p_exp;
	stack<char> stk;
	string operators("+-*/()");
	string str;
	for (int i = 0; i < m_exp.length(); i++) {
		string one;
		if (((m_exp[i] == '-' || m_exp[i] == '+') && (i == 0 || string("+-/*(").find(m_exp[i - 1]) != string::npos)) || isdigit(m_exp[i])) //对于非运算符,进行数字转换
		{          //把操作数加入到后缀式中
			str = m_exp[i] != '+' ? string({ m_exp[i] }) : "";
			while (i + 1 < m_exp.length() && operators.find(m_exp[i+1]) == string::npos) {
				str += m_exp[i + 1];
				i++;
			}
			p_exp.push_back(str);
		}
		else {	//出现操作符
			if (m_exp[i] == '(')         //栈中添加左括号
				stk.push({ m_exp[i] });
			else if (m_exp[i] == ')') {            //出现右括号时,将栈中元素一直弹出,直至弹出左括号
				while (stk.top() != '(') {
					p_exp.push_back({ stk.top() });
					stk.pop();
				}
				stk.pop();                         //弹出左括号
			}
			else {					    //操作符的优先级判断
				while ((!stk.empty()) && (priority[m_exp[i]] <= priority[stk.top()])) {    //当栈不为空时,进行优先级判断
					p_exp.push_back({ stk.top() });   //若当前操作符优先级低于栈顶,弹出栈顶,放到后缀式中
					stk.pop();
				}
				stk.push({ m_exp[i] });             //将当前操作符入栈
			}	
		}		
	}
	while (!stk.empty()) {    //将栈中剩余操作符放到后缀式中
		p_exp.push_back({ stk.top() });
		stk.pop();
	}
	return p_exp;
}
int main() {
	string m_exp;
	cin >> m_exp;
	auto p_exp = trans(m_exp);
	for (int i = 0; i < p_exp.size(); ++i)
		cout << (i ? " " : "") << p_exp[i];
	return 0;
}

 

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值