中缀试转后缀试及前缀试并计算其结果

简介:

/*
        参考大神nb的代码,感觉思路不错!终于搞明白了!一开始不明白在计算表达式的时候,利用栈到底做了什么!现在感觉我们利用栈就是模拟我们书面上计算表达式,
       将优先级高的运算先计算出来,然后放进栈中,等待下一次的计算
*/
#include<iostream> 
#include<string> 
#include<stack>
#include<cstdio>
using namespace std;

class node
{
public:
     double ret;
     string prefix, suffix;//前缀表达式和后缀表达式 
     node()
     {
         ret=0;
         prefix=suffix=""; 
     } 
};

stack<node>optd;//操作数栈
stack<char>optr;//操作符栈

char formula[1000];//表达式以"=" 结束 

int cmp(char ch)//定义符号的优先级
{
   switch(ch)
   {
      case '#': return -2;
      case '=': return -1;
      case '+':
      case '-': return 1;
      case '*':
      case '/': return 2;
      case '(': return 3;
      case ')': return 0;
   }
   return -2;
}

double deal(double x, char ch, double y)
{
   switch(ch)
   {
       case '+': return x+y;
       case '-': return x-y;
       case '*': return x*y;
       case '/': return x/y;
   }
   return 0.0;
}

void cal()
{
   int i=0, n;
   node num, aTmp, bTmp;
   while(optr.top()!='=')
   {
      if(formula[i]>='0' && formula[i]<='9')
      {
           sscanf(formula+i, "%lf%n", &num.ret, &n);
           num.prefix.assign(formula+i, n);
           num.suffix.assign(formula+i, n);
           i+=n;
           optd.push(num);
      }
      else
      {
           if(optr.top()=='(' && formula[i]==')')//消除一对括弧 
           {
         optr.pop();
         ++i;
         }
           if(cmp(formula[i]) > cmp(optr.top()) || optr.top()=='(')//当前运算符大于栈顶运算符直接进栈
     {
         optr.push(formula[i]);
         ++i;
     }
     else
     {
        char ch=optr.top(), preTmp[]={ch, ' ', '\0'}, sufTmp[]={' ', ch, '\0'} ;
        optr.pop();//弹出一个栈顶操作符 
        bTmp=optd.top(); optd.pop();//得到第二个操作数 
        aTmp=optd.top(); optd.pop();//得到第一个操作数 
        aTmp.ret=deal(aTmp.ret, ch, bTmp.ret);
        
        aTmp.suffix+=" " + bTmp.suffix + sufTmp;//得到运算后的后缀式子
        aTmp.prefix=preTmp + aTmp.prefix + " " + bTmp.prefix;//得到运算前的后缀式子
        optd.push(aTmp);//不要忘记将计算的结果放入栈中 
     }
      }
   }
   optr.pop();//别忘记弹出栈顶上的'=' 
}

int main()
{
   optr.push('#');//初始化栈顶操作符是‘#’ 
   while(cin>>formula)
   {
       cal();
       node ans=optd.top(); optd.pop();
       cout<<"表达式结果:"<<ans.ret<<endl<<"前缀试:"<<ans.prefix+'='<<endl<<"后缀试:"<<ans.suffix+'='<<endl; 
   }
   return 0;
}

目录
相关文章
|
机器学习/深度学习 人工智能 前端开发
未来趋势:人工智能在前端开发中的应用
随着人工智能技术的快速发展,前端开发领域也迎来了新的变革。本文将深入探讨人工智能在前端开发中的应用现状,并展望未来的发展趋势,带领读者一窥未来前端开发的可能面貌。
|
机器学习/深度学习 人工智能 编解码
阿里 DSW 试用心得——用 PAI-DSW 修复老照片
通过试用阿里 DSW 了解了命令行和 SD WebUI 两种方式进行老照片修复的相关知识
1409 1
阿里 DSW 试用心得——用 PAI-DSW 修复老照片
|
iOS开发
清除QuickTime Player 在Dock程序右键上的历史记录
清除QuickTime Player 在Dock程序右键上的历史记录
1240 2
清除QuickTime Player 在Dock程序右键上的历史记录
|
索引 Windows
技术笔记:RTF文件格式
技术笔记:RTF文件格式
857 0
|
小程序
小程序一直未上架的原因及解决方案
小程序一直未上架的原因及解决方案
400 11
STM32外设系列—TB6612FNG
本文简单介绍了TB6612FNG,给出了接线方法和控制逻辑。最后,给出了程序设计,利用串口调节占空比来调节电机转速。
870 0
STM32外设系列—TB6612FNG
|
JSON 小程序 开发工具
微信小程序Vant组件配置及使用
微信小程序Vant组件配置及使用
452 1
微信小程序Vant组件配置及使用
|
JavaScript 前端开发 Linux
Vue.js + Electron 的跨平台桌面应用程序开发
本文介绍了 Vue.js 和 Electron 的基本特点和原理,并分析了它们在桌面应用程序开发中的优势和应用场景。在基于 Vue.js 和 Electron 的桌面应用程序开发实践中,本文详细介绍了项目的搭建和配置,包括环境的准备、项目的初始化和依赖的安装等步骤。然后,本文介绍了使用 Vue.js 进行界面设计和组件开发的方法,并提供了相关的示例代码和实现细节。接下来,本文探讨了 Electron 主进程和渲染进程的开发,包括窗口管理、文件系统访问和与底层系统交互等方面的内容。最后,本文对基于 Vue.js 和 Electron 的桌面应用程序开发做出了总结,并展望了未来的发展方向和应用前景
1201 2
|
机器学习/深度学习 人工智能 达摩院
视觉AI技术体系及趋势概述
视觉技术是 AI 里应用最广,任务最多,技术方面非常复杂,发展非常快的一个AI的主要子方向。