概要

表达式求值问题可以说是一个经典问题。具体思路就是首先把输入的中缀表达式转换为后缀表达式,然后再根据后缀表达式进行计算求值。


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

首先我们设定运算符在进栈前与进栈后的优先级:

  1. 首先在栈把“#”进行压栈,并在中缀表达式追加“#”。“#”作为结束标志。
  2. 对中缀表达式进行遍历,遇到数字进行输出到后缀表达式中
  3. 如果遇到运算符,把栈顶的元素(前者)的栈内优先级与即将入栈元素(后者)的栈外优先级进行比较,如前者小,则运算符入栈,否则,则把栈顶元素(前者)出栈并输出到后缀表达式中,然后把后者入栈。
  4. 循环2,3两步直至中缀表达式的尾部的“#”。

后缀表达式求值

对后缀表达式进行遍历,如果是数字就入栈,如果是运算符,就连续出栈两次的结果进行保存,之后进行相应运算,把运算结果入栈,直至遍历结束,结果为栈顶元素。


下面是具体代码,但是为了减小码量,下面的程序对输入数字有如下要求:必须是0-9的数字,大于等于10不行,即如表达式:(1+(10-5)*2+2)/2是不合法的,10以上的数字不能出现。


#include <iostream>
#include <cstring>
#include <string>
using namespace std;//这是把中缀表达式转化成后缀表达式的类
class Transform{private:char* str;int top;int size;public://表达式求值的构造函数 Transform(int size){this->size = size;str = new char[size];top = -1;}//栈是否为空的函数bool IsEmpty(){return top == -1;}//栈是否已满的函数bool IsFull(){return top == this->size-1;}//入栈函数void Push(char ch){if(!this->IsFull()){this->str[++top] = ch;  }}//获得栈顶元素 char Top(){return this->str[top];}//出栈函数void Pop(){this->top--;} //栈外运算符优先级 int icp(char ch){int result = 0;if(ch == '#'){result = 0;}if(ch == '('){result = 6;}if(ch == '*'||ch == '/'){result = 4;}if(ch == '+'||ch == '-'){result = 2;}   if(ch == ')'){result = 1;}return result;      }//栈内运算符优先级 int isp(char ch){int result = 0;if(ch == '#'){result = 0;}if(ch == '('){result = 1;}if(ch == '*'||ch == '/'){result = 5;}if(ch == '+'||ch == '-'){result = 3;}   if(ch == ')'){result = 6;}return result;      }//中缀表达式转为后缀表达式函数string Transform_Median(string median){//在中缀表达式和栈中追加"#"表示结束 median.append("#"); this->Push('#');char* c;int cnt = 0;char* tmp;c = new char[median.length()];tmp = new char[median.length()];            //后缀表达式的暂存数组 strcpy(c,median.c_str());for(int i = 0 ; i < median.length() ; i++){//如果是数字直接输出到后缀表达式中 if(c[i] >= '0' && c[i] <= '9'){tmp[cnt++] = c[i];}else{//如果不是数字,则需要和栈顶元素比较运算符优先级 char ch = this->Top();//栈顶元素在栈内的优先级比栈外元素的优先级高,则栈外元素入栈 if(this->isp(ch) < this->icp(c[i])){this->Push(c[i]); }else if(this->isp(ch) > this->icp(c[i])){//栈顶元素在栈内的优先级比栈外元素的优先级低//则栈内元素出栈,并输出到后缀表达式中,循环变量减1 tmp[cnt++] = ch;this->Pop();i--;}else{//栈顶元素在栈内的优先级等于栈外元素的优先级//说明已经运行到“#”,则出栈即可 this->Pop();    }}}//返回中缀表达式的字符串 string after = string(tmp,cnt);return after;}
}; //这是后缀表达式计算类
class Sum{private:int* sum;int top;int size;public://表达式求值的构造函数 Sum(int size){this->size = size;sum = new int[size];top = -1;}//栈是否为空的函数bool IsEmpty(){return top == -1;}//栈是否已满的函数bool IsFull(){return top == this->size-1;}//入栈函数void Push(int num){if(!this->IsFull()){this->sum[++top] = num; }}//获得栈顶元素 int Top(){return this->sum[top];}//出栈函数void Pop(){this->top--;} //后缀表达式求和int Sum_After(string after){char* s;s = new char[after.length()];strcpy(s,after.c_str());for(int i = 0 ; i < after.length() ; i++){if(s[i] >= '0' && s[i] <= '9'){this->Push(s[i]-'0');}else{int b = this->Top();this->Pop();int a = this->Top();this->Pop();int result = 0;switch(s[i]){case '+': result = a + b ;break;case '-': result = a - b ;break;case '*': result = a * b ;break;case '/': result = a / b ;break;};this->Push(result);}}return this->Top();}
};int main()
{string median;cout<<"请输入中缀表达式:"<<endl;cin>>median;Transform transform(median.length());string after = transform.Transform_Median(median);cout<<"后缀表达式为:"<<endl<<after<<endl;Sum sum(after.length()); int result = sum.Sum_After(after);cout<<"结果为:"<<endl<<result<<endl; return 0;} 

栈的应用——表达式求值相关推荐

  1. php表达式求值,PHP实现基于栈的后缀表达式求值功能

    本文实例讲述了PHP实现基于栈的后缀表达式求值功能.分享给大家供大家参考,具体如下: 后缀表达式概述 后缀表达式,指的是不包含括号,运算符放在两个运算对象的后面,所有的计算按运算符出现的顺序,严格从左 ...

  2. 栈实现算术表达式求值

    算术表达式求值 利用栈求解的一个典型的问题是算术表达式求值,例如:"3+4*2-(1+1)#",这样的表达式计算,在计算过程中,不是读到一个运算就立即计算,而是要与后面的运算符进行 ...

  3. 数据结构课程设计---------用栈来实现表达式求值

    1.需求分析 设计一个程序,演示用算符优先法对算术表达式求值的过程.利用算符优先关系,实现对算术四则混合运算表达式的求值. (1)输入的形式:表达式,例如2*(3+4)      包含的运算符只能有' ...

  4. 基于栈的后缀表达式求值(洛谷P1449题题解,Java语言描述)

    题目要求 P1449题目链接 分析 给出后缀表达式求值,就相当于没了括号,而且很直接. 我们需要使用栈结构来完成任务. Java原装的栈使用了很多synchronized,导致性能不佳,但我们也就将就 ...

  5. 【Java】基于栈的算术表达式求值

    定义异常类 public class ExpressionException extends RuntimeException {private static final long serialVer ...

  6. 栈的应用——表达式求值(双栈)

    1.表达式求值 中缀表达式是正常的表达式形式, 例如:4.99 * 1.06 + 5.99 + 6.99 * 1.06 后缀表达式是针对中缀表达式而言的,可以理解为:操作符在两个操作数之后. 例如:4 ...

  7. 北京林业大学数据结构实验二 基于栈的算术表达式求值算法

    第1关:基于栈的中缀算术表达式求值 参见课本P75 例3.3 #include <iostream> #include<iomanip>#define MAXSIZE 100 ...

  8. 编程题实训-实验2-基于栈的算术表达式求值算法(北京林业大学)

    第1关:基于栈的中缀算术表达式求值 任务描述 本关任务:输入一个中缀算术表达式,求解表达式的值.运算符包括+.-.*./.(.).=,参加运算的数为double类型且为正数.(要求:直接针对中缀算术表 ...

  9. 数据结构栈之中缀表达式求值(实现计算器综合计算)

    一.思路分析: 1.通过一个index值(索引),来遍历我们的表达式. 2.如果我们发现是一个数字,就直接入数栈. 3.如果发现扫描到是一个符号,就分如下情况: (1).如果发现当前的符号栈为空,就直 ...

最新文章

  1. UI设计培训技术分享:配色秘籍
  2. TYVJ1427 小白逛公园
  3. 【Nginx】解决 504 Gateway Time-out
  4. 10亿个字符串的排序问题
  5. shell结合expect写的批量scp脚本工具
  6. excel中怎样用公式获取表单控件_挑战高手:用不到 100 行代码,在前端实现 Excel 全部功能...
  7. 你的Parquet该升级了:IOException: totalValueCount == 0问题定位之旅
  8. Lazy Load Plugin for jQuery延迟加载测试成功
  9. sose会议级别_【2017年整理】计算机领域EI和SCI收录期刊、影响因子及国际会议.doc...
  10. java中md5加密和解密_java的MD5加密与解密
  11. 推荐5款常用编程文本编辑器
  12. 51单片机的红外遥控
  13. Python-伪数据构造神库Faker
  14. 因IP被列入黑名单导致U-Mail被退信的处理方法
  15. 自动回复的三种形式?
  16. java经典题之冒泡排序
  17. 2022眼视光展,护眼产品展,眼睛健康展,视力康复展
  18. HTML基础知识点总结
  19. 人工智能会拥有意识吗?
  20. C# 输入一个三位数的字符串,输出为三位数的整数,并输出百位、十位、和个位

热门文章

  1. 基于Flash播放器的P2P直播解决方案
  2. 《大话设计模式》php版本
  3. 通过百度云加速,实现网站域名可以被ipv6访问解析
  4. 360手机刷机救砖:QGDP360手机全支持;360手机N5、N5S、N6、N6Lite、N6PRO、N7、N7Lite、N7PRO
  5. 局域网内环境搭建-PC篇
  6. 选择法排序的两种方法
  7. virgo,基于osgi的模块化运行容器
  8. 3.7PPP协议和HDLC协议
  9. 现代远程教育入学指南(石油大学)--入学篇---在线考试
  10. Ubuntu10.10 32位系统下moses统计机器翻译系统使用命令记录