中缀表达式转后缀表达式详细思路及代码实现
什么是中缀表达式?
中缀表达式是一个通用的算术或逻辑公式表示方法, 操作符是以中缀形式处于操作数的中间(eg:3+4、3+4*2、8+(17-6*2)….)。
为什么要中缀表达式转后缀表达式?
但是中缀表达式不易被计算机处理。我们在计算一个式子(通常为中缀表达式)时,需要将中缀表达式转化为后缀表达式。
什么是后缀表达式?
那么后缀表达式,又称逆波兰式,指的是不包含括号,运算符放在两个运算对象的后面,所有的计算按运算符出现的顺序,严格从左向右进行(不再考虑运算符的优先规则)。一般用栈来模拟。
怎么把中缀表达式转成后缀表达式呢?
举一个简单的栗子:
(3+4)×5-2
画成树大概是这样的:
所以后缀表达式为:
3 4 + 5 × 2 -
以下是转换的思路:
1.初始化两个字符型数组模拟栈:字符存入栈s1和储存中间结果的栈s2;
2.从左至右扫描中缀表达式;
3.遇到操作数时,将其压s2;
4.遇到运算符时,比较其与s1栈顶运算符的优先级:
如果s1为空,或栈顶运算符为左括号“(”,则直接将此运算符入栈;
否则,若优先级比栈顶运算符的高,也将运算符压入s1;
否则,将s1栈顶的运算符弹出并压入到s2中,再次转到①与s1中新的栈顶运算符相比较;
5.遇到括号时:
如果是左括号“(”,则直接压入s1;
如果是右括号“)”,则依次弹出s1栈顶的运算符,并压入s2,直到遇到左括号为止,此时将这一对括号丢弃;
6.重复步骤2至5,直到表达式的最右边;
7.将s1中剩余的运算符依次弹出并压入s2;
8.依次弹出s2中的元素并输出,结果的逆序即为中缀表达式对应的后缀表达式
然后就可以按照后缀表达式来计算了。
一定要注意取出元素的计算顺序!先取出的数为
X
数
(X为减/除/加/乘),后取出的数为被
X
数
!
代码(有详细注释):
#include<bits/stdc++.h>//万能头文件
using namespace std;
#define IOS ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);//加速语句
typedef long long ll;
const int N=1e5+10;
char s1[N],s2[N],s[N];
ll top1,top2,p,js[N],topis;int lev(char n)
{if(n=='+'||n=='-') return 1;if(n=='*'||n=='/') return 2;if(n=='^') return 3;return 0;
}
void print()
{for(int i=1;i<=topis;i++)//当前正在算的{cout<<js[i]<<' ';}for(int i=p+1;i<=top2;i++)//后面还没有遍历到的{cout<<s2[i];if(i!=top2)cout<<" ";}if(p!=top2)cout<<endl;
}
int main()
{cin>>s;for(int i=0;i<strlen(s);i++){if(s[i]<='9'&&s[i]>='0'){s2[++top2]=s[i];}else{if(s[i]=='('){s1[++top1]=s[i];continue;}if(s1[top1]=='('||top1==0){s1[++top1]=s[i];continue;}if(lev(s1[top1])>=lev(s[i])&&s[i]!=')')//当进来的不是右括号,且进来的符号优先级没有s1的栈顶符号优先级高//这个时候需要将s1的栈顶元素给到s2中{s2[++top2]=s1[top1--];while(lev(s1[top1])>=lev(s[i]))//若优先级任然没有要进来的符号优先级高,持续的给到s2中{s2[++top2]=s1[top1--];}//循环结束后,要进来的符号优先级没有s1的栈顶符号优先级高,则可以存入s1中s1[++top1]=s[i];continue;}if(lev(s1[top1])<lev(s[i])&&s[i]!=')'){s1[++top1]=s[i];}if(s[i]==')')//遇到了 ' ) '{while(s1[top1]!='(')//将s1中的符号依次给到s2中,直到遇到 ' ) '{s2[++top2]=s1[top1--];}top1--;continue;}}}while(top1>0)//若s1还有符号的话,需要给到s2中{s2[++top2]=s1[top1--];}for(int i=1;i<=top2;i++){cout<<s2[i]<<" ";}cout<<endl;//完美完成中缀转后缀//接下来依次计算for(int i=1;i<=top2;i++){p=i;if(s2[i]>='0'&&s2[i]<='9'){js[++topis]=s2[i]-'0';}else //为符号,对栈顶两个元素进行运算,并将结果存入栈顶{//注意先进栈的做运算的第一位数if(s2[i]=='+'){ll x=js[topis];ll y=js[--topis];ll ans=y+x;js[topis]=ans;}if(s2[i]=='-'){ll x=js[topis];ll y=js[--topis];ll ans=y-x;js[topis]=ans;}if(s2[i]=='*'){ll x=js[topis];ll y=js[--topis];ll ans=y*x;js[topis]=ans;}if(s2[i]=='/'){ll x=js[topis];ll y=js[--topis];ll ans=y/x;js[topis]=ans;}if(s2[i]=='^'){ll x=js[topis];ll y=js[--topis];ll ans=pow(y,x);js[topis]=ans;}print();//每一步都要打印}}return 0;
}
运行结果如下:
中缀表达式转后缀表达式详细思路及代码实现相关推荐
- 前缀表达式,中缀表达式和后缀表达式的定义与联系(超详细)
目录 前缀.中缀.后缀表达式 前缀表达式 前缀表达式的计算机求值 中缀表达式 后缀表达式 后缀表达式的计算机求值 中缀表达式转化为前缀和后缀表达式 小结 前缀.中缀.后缀表达式 前缀.中缀.后缀表达式 ...
- java中缀表达式转后缀表达式_数据结构Java实现06----中缀表达式转换为后缀表达式...
本文主要内容: 表达式的三种形式 中缀表达式与后缀表达式转换算法 一.表达式的三种形式: 中缀表达式:运算符放在两个运算对象中间,如:(2+1)*3.我们从小做数学题时,一直使用的就是中缀表达式. 后 ...
- 【Weiss】【第03章】练习3.20:中缀表达式转后缀表达式
[练习3.20] a.编写一个程序将中缀表达式转换为后缀表达式,该中缀表达式含括号及四则运算. b.把幂操作符添加到你的指令系统中去. c.编写一个程序将后缀表达式转化为中缀表达式. Answer: ...
- 逆波兰表达式中缀表达式转换为后缀表达式
中缀表达式转换为后缀表达式 思路分析 代码实现 package com.atguigu.stack;import javax.swing.plaf.nimbus.State; import java. ...
- 数据结构 - 栈 (逆波兰计算器)(栈的三种表达式)(前缀、中缀和后缀表达式,后缀也叫逆波兰表达式)(中缀表达式转后缀表达式实现步骤及完整代码)
栈的三种表达式:前缀.中缀和后缀表达式,后缀也叫逆波兰表达式 前缀(波兰表达式) 中缀(对人来讲很好理解,对于计算机来讲就方便了,一般会把中缀表达式转换成后缀表达式) 后缀(逆波兰表达式) 计算过程 ...
- 中缀表达式到前缀表达式和后缀表达式
1.算法思路 转化为后缀:从左到右遍历中缀表达式,遇到操作数,输出,遇到操作符,当前操作符的优先级大于栈顶操作符优先级,进栈,否则,弹出栈顶优先级大于等于当前操作符的操作符,当前操作符进栈. ...
- 逆波兰式 java_逆波兰式(后缀表达式)的计算 中缀表达式转后缀表达式(逆波兰式)【java实现】...
一.逆波兰式(后缀表达式)计算 思路: * 1.遍历逆波兰式的集合 * 2.当遍历的元素为数字时,入栈 stack * 3.当遍历的元素为运算符时,stack栈弹出两个数,num2 num1,并用该运 ...
- 数据结构(3) 第三天 栈的应用:就近匹配/中缀表达式转后缀表达式 、树/二叉树的概念、二叉树的递归与非递归遍历(DLR LDR LRD)、递归求叶子节点数目/二叉树高度/二叉树拷贝和释放...
01 上节课回顾 受限的线性表 栈和队列的链式存储其实就是链表 但是不能任意操作 所以叫受限的线性表 02 栈的应用_就近匹配 案例1就近匹配: #include <stdio.h> in ...
- Java中缀表达式转后缀表达式.
有点不好写,大家可以看看这个思路,当然有多种方法! package zhan;import java.util.ArrayList; import java.util.List; import jav ...
最新文章
- WSGI 是什么?和nginx有什么关系?
- HTML5学习笔记(二十七):Ajax
- 从网上批量下载图片并重命名
- Beautifulsoup的使用
- 织梦 mysql 配置文件_MySQL集群配置
- ASP.NET 自定义项目模板
- thinkphp3 php jwt,thinkphp框架使用JWTtoken的方法详解
- Deepin系统安装后相关设置与环境搭建
- 三分钟看Netty(3) select poll VS epoll
- 计算机多媒体教室管理制度,新疆大学多媒体教室管理制度
- 《人工智能 智能系统指南》
- No serializer found for class
- import java.io 是什么意思_Java IO 详解
- Protobuf简单使用
- 微信公众号(订阅号)文章阅读数监控V0.1
- 飞机机身结构主要分三种,现在大部分飞机都用第三种
- Java调用Python下载网页
- 数学建模-火箭发射问题
- Docker常用工具
- 差分详细讲解(C++)
热门文章
- Matlab绘制三维定限截面柱体;已知(隐)函数方程,绘制三维空间图形
- STM32系列 (一)开发环境的搭建
- 为什么修改jsp不用重启tomcat,而修改servlet要重启tomcat
- SQLserver创建代理作业
- 算法日记(十三)之动态规划
- python去掉最后一行的换行符_python去掉行尾的换行符方法
- THU.文本处理三剑客
- oracle数据库系统学习,Oracle数据库学习第二天
- 37种传感器(十七)之有水银开关模块+Stduino NanoUNO
- 一款学习笔记或者计划笔记纸的应用:A4打印纸和手帐笔记,手帐素材全部拿下