前缀、中缀、后缀表达式(逆波兰表达式)

2023-11-15

中缀表达式

简介

中缀表达式就是常见的运算表达式,如(3+4)×5-6

前缀表达式

简介

前缀表达式又称波兰式,前缀表达式的运算符位于操作数之前

比如:- × + 3 4 5 6

前缀表达式的计算机求值

从右至左扫描表达式,遇到数字时,将数字压入堆栈,遇到运算符时,弹出栈顶的两个数,用运算符对它们做相应的计算(栈顶元素 op 次顶元素),并将结果入栈;重复上述过程直到表达式最左端,最后运算得出的值即为表达式的结果

  • 例如:- × + 3 4 5 6

    1. 从右至左扫描,将6、5、4、3压入堆栈
    2. 遇到+运算符,因此弹出3和4(3为栈顶元素,4为次顶元素,注意与后缀表达式做比较),计算出3+4的值,得7,再将7入栈
    3. 接下来是×运算符,因此弹出7和5,计算出7×5=35,将35入栈
    4. 最后是-运算符,计算出35-6的值,即29,由此得出最终结果

将中缀表达式转换为前缀表达式

转换步骤如下:

  1. 初始化两个栈:运算符栈s1,储存中间结果的栈s2
  2. 从右至左扫描中缀表达式
  3. 遇到操作数时,将其压入s2
  4. 遇到运算符时,比较其与s1栈顶运算符的优先级
    1. 如果s1为空,或栈顶运算符为右括号“)”,则直接将此运算符入栈
    2. 否则,若优先级比栈顶运算符的较高或相等,也将运算符压入s1
    3. 否则,将s1栈顶的运算符弹出并压入到s2中,再次转到(4-1)与s1中新的栈顶运算符相比较
  5. 遇到括号时
    1. 如果是右括号“)”,则直接压入s1
    2. 如果是左括号“(”,则依次弹出S1栈顶的运算符,并压入S2,直到遇到右括号为止,此时将这一对括号丢弃
  6. 重复步骤2至5,直到表达式的最左边
  7. 将s1中剩余的运算符依次弹出并压入s2
  8. 依次弹出s2中的元素并输出,结果即为中缀表达式对应的前缀表达式

后缀表达式

简介

后缀表达式又称逆波兰表达式,与前缀表达式相似,只是运算符位于操作数之后

比如:3 4 + 5 × 6 -

后缀表达式计算机求值

与前缀表达式类似,只是顺序是从左至右:

从左至右扫描表达式,遇到数字时,将数字压入堆栈,遇到运算符时,弹出栈顶的两个数,用运算符对它们做相应的计算(次顶元素 op 栈顶元素),并将结果入栈;重复上述过程直到表达式最右端,最后运算得出的值即为表达式的结果

例如后缀表达式“3 4 + 5 × 6 -”

  1. 从左至右扫描,将3和4压入堆栈;
  2. 遇到+运算符,因此弹出4和3(4为栈顶元素,3为次顶元素,注意与前缀表达式做比较),计算出3+4的值,得7,再将7入栈;
  3. 将5入栈;
  4. 接下来是×运算符,因此弹出5和7,计算出7×5=35,将35入栈;
  5. 将6入栈;
  6. 最后是-运算符,计算出35-6的值,即29,由此得出最终结果。

将中缀表达式转换为后缀表达式

与转换为前缀表达式相似,步骤如下:

  1. 初始化两个栈:运算符栈s1和储存中间结果的栈s2;
  2. 从左至右扫描中缀表达式;
  3. 遇到操作数时,将其压s2;
  4. 遇到运算符时,比较其与s1栈顶运算符的优先级:
    1. 如果s1为空,或栈顶运算符为左括号“(”,则直接将此运算符入栈;
    2. 否则,若优先级比栈顶运算符的高,也将运算符压入s1(注意转换为前缀表达式时是优先级较高或相同,而这里则不包括相同的情况);
    3. 否则,将s1栈顶的运算符弹出并压入到s2中,再次转到(4-1)与s1中新的栈顶运算符相比较;
  5. 遇到括号时:
    1. 如果是左括号“(”,则直接压入s1;
    2. 如果是右括号“)”,则依次弹出s1栈顶的运算符,并压入s2,直到遇到左括号为止,此时将这一对括号丢弃;
  6. 重复步骤2至5,直到表达式的最右边;
  7. 将s1中剩余的运算符依次弹出并压入s2;
  8. 依次弹出s2中的元素并输出,结果的逆序即为中缀表达式对应的后缀表达式(转换为前缀表达式时不用逆序)

 

那么一些朋友可能会问既然中缀表达式最符合人类的思维习惯,为什么还需要前缀表达式和后缀表达式?先看一个例子,假如在前面的表达式基础上加一点东西:

  3+2*5

  此时的表达式很显然,如果进行计算,则先计算2*5,最后计算加法。但是如果需要先计算加法运算呢?则必须加上括号,(3+2)*5。

  而如果用后缀表达式来表示,则为 32+5*,那么该表达式的计算顺序为3+2 —> (3+2)*5。

  区别就在这里,后缀表达式不需要用括号就能表示出 整个表达式哪部分运算先进行。同理,前缀表达式也是如此。这种表达式正好最符合计算机的处理方式,因为后缀表达式和前缀表达式求值不需要考虑优先级的问题,计算机处理起来便简单很多。

  今天我们这里主要讲解中缀表达式和后缀表达式(前缀表达式和后缀表达式很类似,就不做过多赘述),下面是讲解大纲:

  • 中缀表达式如何直接求值?
  • 后缀表达式如何直接求值?
  • 中缀表达式如何转换为后缀表达式?

1.中缀表达式直接求值

  对于中缀表达式求值来说,一般最常见的直接解决办法就是利用栈,一个栈用来保存操作数,一个栈用来保存操作符。

2.后缀表达式直接求值

  由于后缀表达式不需要用括号来表示计算顺序,因此处理起来比较简单。

3.中缀表达式如何转为后缀

  大部分数据结构教材在讲述 栈的时候都会涉及到中缀表达式转为后缀表达式的问题,因为这个是栈的典型应用之一。因此很多教材上都会利用栈来进行转换,这里我们来讨论一下最常见的两种转换思路和一种简便的验证方法。

  • 利用二叉树进行转换

  由于二叉树本身结构的特殊性,使得我们可以利用它来很轻松地将中缀表达式转变成后缀表达式,事实上,只要根据中缀表达式建立好相应的二叉树之后,直接对二叉树进行前序遍历和后序遍历便可得到前缀表达式和后缀表达式。在利用二叉树来表示表达式时,用叶子节点来存储操作数,用内部节点存储操作符,比如这样一个表达式3*5+5/2+(3+5)*2,表示成二叉树的形式(注意其有等同的其他形式)就是:

  

  其实讲中缀表达式的过程转变成二叉树的形式是一个递归的过程,比如有一个表达式,其对应的的二叉树的根节点必定是优先级最低的操作符(也就是说是整个表达式中最后进行的运算操作),然后再在操作符的左部分中找出最后进行的操作符作为根节点的左孩子,在操作符的右部分中找出最后进行的操作符作为根节点的右孩子,然后知道左部分或者右部分是单纯的操作数,则作为叶子节点,直到整个二叉树建立完毕。

  • 利用栈进行转换

  利用栈进行转换的思路其实跟前面直接对中缀表达式求值的过程类似,在这过程中需要一个栈用来保存操作符optStack,需要一个数组用来保存后缀表达式suffix[],然后从头到尾扫描表达式

  1)如果遇到操作符,则跟optStack的栈顶操作符比较优先级,如果大于栈顶操作符的优先级,则入栈,否则不断取栈顶操作符加到suffix的末尾,直到栈顶操作符优先级低于该操作符,然后将该操作符入栈;

  2)遇到操作数,直接加到suffix的末尾

  3)遇到左括号,入栈;

  4)遇到右括号,则依次弹出栈顶操作符加到suffix的末尾,直到遇到左括号,然后将左括号出栈。

  • 简便验证办法

  最后一种办法可以很快速地求出中缀表达式对应的前缀表达式和后缀表达式,就是添括号去括号法。

  比如有表达式: (3+5*2)-2*3

  先对每一个小部分添加括号: ((3+(5*2))-(2*3))

  然后将每个操作符放到括号后面:((3(52)*)+(23)*)-

  然后去括号:352*+23*-

  便得到了后缀表达式,前缀表达式类似(只需把操作符放到括号前面即可)。

 

转载自:https://www.cnblogs.com/dolphin0520/p/3708602.html

              https://www.cnblogs.com/chensongxian/p/7059802.html

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

前缀、中缀、后缀表达式(逆波兰表达式) 的相关文章

  • C语言/C++实现栈操作

    一 栈的概念 栈是一种常用的数据结构 它遵循先入后出 Last In First Out LIFO 的原则 栈的操作只在栈的一端进行 该端被称为栈顶 而另一端称为栈底 栈的基本操作包括压栈 入栈 push 和弹栈 出栈 pop 分别用于将元
  • Mysql 数据库

    数据库基础 1 什么是数据库 用来存储数据 数据库可在硬盘及内存中存储数据 数据库与文件存储数据的区别 数据库本质也是通过文件来存储数据 数据库的概念就是系统的管理存储数据的文件 数据库介绍 本质就是存储数据的C S架构的socket套接字
  • 算法--将数组分成和相等的多个子数组,求子数组的最大个数

    作者 陈太汉 一个整数数组 长度为n 将其分为m份 使各份的和相等 求m的最大值 比如 3 2 4 3 6 可以分成 3 2 4 3 6 m 1 3 6 2 4 3 m 2 3 3 2 4 6 m 3 所以m的最大值为3 算法 原理的思想是
  • BP神经网络与Python实现

    人工神经网络是一种经典的机器学习模型 随着深度学习的发展神经网络模型日益完善 联想大家熟悉的回归问题 神经网络模型实际上是根据训练样本创造出一个多维输入多维输出的函数 并使用该函数进行预测 网络的训练过程即为调节该函数参数提高预测精度的过程
  • Hash映射理解

    先说数组 数组优点之一 能通过索引很快定位到值 hashmap 就是利用了数组这个优点 对比 线性映射 定义一个数组 数组的元素是结构体 结构体包括 一对键 值 伪代码表示 a 0 struct Bill 5 a 1 struct KK 6
  • 亚利桑那州立大学周纵苇:研习 U-Net ——现有的分割网络创新

    雷锋网AI研习社按 经典的 Encoder Decoder 结构在目标分割问题中展现出了举足轻重的作用 然而这样一个相对固定的框架使得模型在感受野大小和边界分割精度两方面很难达到兼顾 本次公开课 讲者以 U Net 为案例分析 总结现有的分
  • 算法系列15天速成——第八天 线性表【下】

    一 线性表的简单回顾 上一篇跟大家聊过 线性表 顺序存储 通过实验 大家也知道 如果我每次向 顺序表的头部插入元素 都会引起痉挛 效率比较低下 第二点我们用顺序存储时 容 易受到长度的限制 反之就会造成空间资源的浪费 二 链表 对于顺序表存
  • 数据结构与算法书籍推荐

    学习数据结构与算法 还是很有必要看几本相关的书籍 但根据不同基础的人 合适看的书也不一样 因此 针对不同层次 不同语言的人 推荐几本市面上口碑不错的书 1 入门级 针对刚入门的同学 建议不要急着去看那些经典书 像 算法导论 算法 这些比较经
  • 如何防止过拟合和欠拟合

    过拟合和欠拟合是模型训练过程中经常出现的问题 两种情况正好相反 现将两者的定义及如何防止进行简要总结 1 过拟合 1 1 定义 是指模型对于训练数据拟合呈现过当的情况 反映到评估指标上就是模型在训练集上的表现很好 但是在测试集上的表现较差
  • 人工智能概念

    人工智能概念 人工智能就是用人工方法在机器 计算机 上实现的智能 或称机器智能 即是研究如何用计算机来表示和执行人类的智能活动 以模拟人脑所从事的推理 学习 思考和规划等思维活动 并解决需要人类的智力才能处理的复杂问题 如医疗诊断 管理决策
  • 数理统计知识整理——回归分析与方差分析

    题记 时值我的北科研究生第一年下 选学 统计优化 课程 备考促学 成此笔记 以谨记 1 线性回归 1 1 原理分析 要研究最大积雪深度x与灌溉面积y之间的关系 测试得到近10年的数据如下表 使用线性回归的方法可以估计x与y之间的线性关系 线
  • 时间复杂度+常见复杂度解释

    前言 算法的效率 虽然计算机能快速的完成运算处理 但实际上 它也需要根据输入数据的大小和算法效率来消耗一定的处理器资源 要想编写出能高效运行的程序 我们就需要考虑到算法的效率 算法的效率主要由以下两个复杂度来评估 时间复杂度 评估执行程序所
  • 区块链中的哈希算法

    区块链中的密码学 密码学在区块链中的应用主要有两个 哈希算法与非对称加密算法 这次主要对哈希算法进行详细的说明 哈希算法 哈希算法的特点有 1 输入可以为任意大小的字符串 2 产生固定大小的输出 3 可以在合理的时间内算出输出值 若要满足密
  • 【试题】排列组合

    在写一个远程的代码 如果本地有M个显示器 远程有N个显示器 M lt N 依据分辨率 显示器刷新频率等要求 需要对远程的N个显示器进行最佳分辨率修改 之后 需要从N个远程显示器中选择M个 跟本地显示器进行一对一的匹配 即从 A N M N
  • 插入排序超详解释,一看就懂

    目录 一 插入排序的相关概念 1 基本思想 2 基本操作 有序插入 二 插入排序的种类 三 直接插入排序 1 直接插入排序的过程 顺序查找法查找插入位置 2 使用 哨兵 直接插入排序 四 直接插入排序算法描述 五 折半插入排序 1 查找插入
  • 基数排序代码实现

    详情请看排序总结 传送门 https blog csdn net m0 52711790 article details 121914543 基数排序的知识点我就不贴出来 相信都能搜到对应概念解释 下面就直接上代码 代码解释其实也很清晰了
  • 雪糕的最大数量 排序+贪心

    雪糕的最大数量 雪糕的最大数量 题目描述 样例 数据范围 思路 代码 题目描述 夏日炎炎 小男孩 Tony 想买一些雪糕消消暑 商店中新到 n 支雪糕 用长度为 n 的数组 costs 表示雪糕的定价 其中 costs i 表示第 i 支雪
  • 用两个栈实现队列

    目录 一 栈的基本结构及其接口 二 我的队列结构定义 三 我的队列创建及其初始化 四 我的队列入队 五 我的队列出队 六 我的队列取队头元素 七 我的队列判空 八 我的队列销毁 一 栈的基本结构及其接口 栈的结构定义 typedef int
  • 【数据结构】单链表的定义和操作

    目录 1 单链表的定义 2 单链表的创建和初始化 3 单链表的插入节点操作 4 单链表的删除节点操作 5 单链表的查找节点操作 6 单链表的更新节点操作 7 完整代码 嗨 我是 Filotimo 很高兴与大家相识 希望我的博客能对你有所帮助
  • 排序:计数排序

    一 概念 计数排序是非比较排序 是对哈希直接定址法的变形应用 二 思想 利用数组统计相同数据出现的次数 例如整型数据m出现n次 就在数组m位置记录数据为n 最后从头遍历数组打印数据即可 通俗来讲就是 数组下标即为数据 下标所指位置的值即为数

随机推荐

  • Java编程工具(12):idea中Compile、Make和Build的区别

    目录 1 build rebuild和recompile 2 Compile Make和Build的区别 1 build rebuild和recompile 标注 1 Build Project 编译项目 标注 2 Build Module
  • 读完这个我懂了JNDI

    JNDI 是什么 JNDI是 Java 命名与目录接口 Java Naming and Directory Interface 在J2EE规范中是重要的规范之一 不少专家认为 没有透彻理解JNDI的意义和作用 就没有真正掌握J2EE特别是E
  • 分区表正被其它程序独占访问_硬盘主引导记录MBR程序代码分析——小白到高手的进阶...

    MBR是什么 MBR 全称为Master Boot Record 即硬盘的主引导记录 为了便于理解 一般将MBR分为广义和狭义两种 广义的MBR包含整个扇区 引导程序 分区表及分隔标识 也就是上面所说的主引导记录 而狭义的MBR仅指引导程序
  • java安全沙箱机制介绍

    java安全沙箱机制介绍 组成Java沙箱的基本组件如下 类加载体系结构 class文件检验器 内置于Java虚拟机 及语言 的安全特性 安全管理器及Java API Java安全模型的前三个部分 类加载体系结构 class文件检验器 Ja
  • 综合指数:拉氏指数和派氏指数

    2019独角兽企业重金招聘Python工程师标准 gt gt gt 拉式公式 报告期p1 基期q0之和 除以 基期p0 基期q0 p0 q0是假定的 可以这么理解 如果按照基期的价格 那么现在有多少销售额呢 派式公式
  • 08-3_Qt 5.9 C++开发指南_Graphics View绘图架构

    文章目录 1 场景 视图与图形项 1 1 场景 1 2 视图 1 3 图形项 2 Graphics View 的坐标系统 2 1 图形项坐标 2 2 视图坐标 2 3 场景坐标 2 4 坐标映射 3 Graphics View 相关的类 3
  • 常用的测试平台

    测试用例管理与bug管理平台 测试用例管理平台 jira 推荐方案 定制性很强 redmine 推荐方案 开源 活跃 定制性很强 Testlink 流行的测试用例管理平台 体验不是很好 其它 tapd 云效 禅道 gitlab 在线协作文档
  • 巧用符号链接移动文件夹位置

    有些时候我们可能因为系统或者某些软件的缓存占得比较多 想把他们从C盘移动到其他地方 但是软件本身并没有提供修改缓存文件夹的功能 这下应该怎么办呢 其实还真有一个好办法可以完美解决 这就是今天要为大家介绍的符号链接 符号链接这个名词经常使用L
  • Django中解决redis-py versions 3.2.0 or later. You have 2.10.6版本问题

    问题描述 在django项目中 添加异步任务 跑服务时遇到redis py版本问题 如下截图 提示版本较低 解决 从4 3 0到4 4 0的Kombu更新停止了对redis py v2 10 6的支持 因此迫使我们升级redis py版本
  • Python基础知识(注释、变量、常量)

    注释 是对代码进行解释和说明 注释是给人看的 机器是不运行的 Python中注释 单行注释 注释内容 多行注释 注释内容 或者 注释内容 变量 可以发生改变的一个量 变量是用来区分不同数据的 可以指向一个内存空间 帮我们存储一些数据 变量的
  • pip安装opencv-python不成功

    一个比较笨但还算有效的方法 如果你的python版本较低 如现在2023 07 04使用python3 6环境 使用pip默认安装会是最新的4 8 0 7版本 但事实上这个版本不支持py3 6环境 所以你需要去这里查支持py3 6的最近的一
  • Unity在development模式下的一个坑

    最近发现unity生成的包在Nexus上如果打开带Input控件的界面时 关闭屏幕再打开 则永远无法显示输入法界面了 一开始还以为是unity自己本身的bug 后来发现release版本并无这个问题 于是弄了个最简单的测试版本分别打了 两个
  • day01-编程题

    选择题 题目1 单选 下列属于是计算机硬件的是 D 选项 A QQ B 微信 C 飞秋 D CPU 题目2 单选 下列可以保证java程序跨平台运行的是 A 选项 A JVM java虚拟机 B Windows系统 C Linux系统 D
  • JAVA第三方技术---Elasticsearch---与JDK版本对应关系

    JAVA第三方技术 Elasticsearch 与JDK版本对应关系 目录 文章目录 1 对应关系表 2 Elastic support地址 3 JVM support地址 后记 内容 1 对应关系表 Elasticsearch and J
  • windows 下配置redis 让其他主机访问本机的redis数据

    在做一个分布式项目的时候 redis不使用 ip 127 0 0 1 启动的时候一直报错 即使使用本机的地址也会报错 然后自己去网上找了一些资料都没有解决 网上一些资料又说改配置文件 把 redis windows conf 里面的 pro
  • 10分钟内用Ezo和Python构建以太坊Oracle

    上一篇 我写了用Web3 js构建以太坊Oracle 这个练习给了我一些新的Web3 js 1 0版本知识 许多新的好东西可供选择而且使用它实现一个简单的oracle非常容易 但是 显然必须有更好的方法 Instant Oracles 只需
  • SQL语句中的日期计算

    SQL语句中的日期计算 1 本月的第一天 SELECT DATEADD mm DATEDIFF mm 0 getdate 0 2 本月的最后一天 SELECT dateadd ms 3 DATEADD mm DATEDIFF m 0 get
  • hotmail手机端_hotmail邮箱登陆手机版 参见http://help.

    讲到邮箱 我们很多人都知道 有人问hotmail邮箱 还有人问hotmail邮箱登陆手机版 这到底是咋回事 实际上hotmail邮箱呢 小编为大家带来hotmail邮箱登陆手机版 希望你喜欢 hotmail邮箱登陆手机版 您好 你手机如果是
  • C#软件外包开发流程

    C 是一种由微软开发的多范式编程语言 常用于开发各种类型的应用程序 从桌面应用程序到移动应用程序和Web应用程序 下面和大家分享 C 编程学习流程 希望对大家有所帮助 北京木奇移动技术有限公司 专业的软件外包开发公司 欢迎交流合作 1 基础
  • 前缀、中缀、后缀表达式(逆波兰表达式)

    中缀表达式 简介 中缀表达式就是常见的运算表达式 如 3 4 5 6 前缀表达式 简介 前缀表达式又称波兰式 前缀表达式的运算符位于操作数之前 比如 3 4 5 6 前缀表达式的计算机求值 从右至左扫描表达式 遇到数字时 将数字压入堆栈 遇