第一篇博客嘎嘎
问题描述:读入一个只包含 +, -, *, / 的非负整数计算表达式,计算该表达式的值。
思路:建立两个栈,分别是:运算符栈,用于中缀表达式转化为后缀表达式;操作数栈,用于后缀表达式的计算
#include <iostream> #include <cstdio> #include <vector> #include <stack> #include <cstring> #include <stdlib.h> #include <stdio.h> using namespace std; struct stNode { int nType; //元素的类型,0操作数,1操作符 double nNum; //操作数 char cOp; //操作符 }; stack<char> sop; //运算符栈,用于中缀表达式转换成后缀表达式 stack<double> sNum; //操作数栈,用于后缀表达式的计算 char cExp[1024]; //读入的字符表达式 vector<stNode> SuffixExp; //后缀表达式 inline float GetNum(const char* p, int& k) { int n = atoi(p); k = 0; while (isdigit(p[k])) ++k; return n; } inline int get_ip(char c) //获取栈内优先级 { switch (c) { case '#': return 0; case '+': case '-': return 3; case '*': case '/': return 5; } return 99; } inline int get_op(char c) //获取栈外优先级 { switch (c) { case '#': return 0; case '+': case '-': return 2; case '*': case '/': return 4; } return 99; } int main(void) { memset(cExp, 0, sizeof(cExp)); //初始化栈 while(cin.getline(cExp, 1024)) { //读入字符表达式 if(strlen(cExp)==1 && cExp[0]=='0') break; strcat(cExp, "#"); while (!sop.empty()) //清空操作符栈 sop.pop(); sop.push('#'); //放入界定符 //将中缀表达式转化成后缀表达式 char *p = cExp; while (p[0] != '\0') { if (p[0] == ' ') //空格跳过 { ++p; continue; } if (isdigit(p[0])) { //数字输出到后缀表达式 int k; double n = GetNum(p, k); stNode stTemp; stTemp.nType = 0; stTemp.nNum = n; stTemp.cOp = 0; SuffixExp.push_back(stTemp); p += k; } else { char ch1 = p[0]; char ch2 = sop.top(); if (get_op(ch1) > get_ip(ch2)) { sop.push(ch1); ++p; } else if (get_op(ch1) < get_ip(ch2)) { //输出到后缀表达式 stNode stTemp; stTemp.nType = 1; stTemp.nNum = 0; stTemp.cOp = ch2; SuffixExp.push_back(stTemp); sop.pop(); } else { sop.pop(); ++p; } } } //后缀表达式的计算 while (!sNum.empty()) //清空操作数栈 sNum.pop(); for (int i = 0; i < (int)SuffixExp.size(); ++i) { if (SuffixExp[i].nType == 0) sNum.push(SuffixExp[i].nNum); else { double y = sNum.top(); sNum.pop(); double x = sNum.top(); sNum.pop(); switch (SuffixExp[i].cOp) { case '+': x += y; break; case '-': x -= y; break; case '*': x *= y; break; case '/': x /= y; break; } sNum.push(x); } } printf("%.2f\n", sNum.top()); //输出结果 return 0; } }
知识点:atoi()、memset()【https://blog.csdn.net/qq_27522735/article/details/53374765】、printf("%.2f\n", x)【保留两位小数】