【C++】C++顺序栈实现的计算器
2016-09-08 14:05
302 查看
实现原理
该计算器数据存储是通过声明一个栈模板,来创建一个 int 类型和 char 类型的栈。int 栈存储表达式中的数字,char 类型的栈存储表达式中的运算符。在输入表达式时,通过在表达式首尾添加 “#” 来使程序建立表达式的结束条件。当首尾 “#” 相遇时,即表达式已经计算完成,最后输出结果。
当前源代码中只能计算+、-、*、/,以及(),可以将操作数栈改为 double 类型来计算浮点数。
表达式的计算情况处理如下:
1.如果栈顶运算符的优先级低于当前所扫描运算符的优先级,则栈顶的运算符不能计算,故当前扫描的运算符要入栈,然后继续扫描其后续符号。
2.如果栈顶的运算符的优先级高于当前所扫描运算符的优先级,则要取出栈顶运算符进行运算。此时,栈顶运算符的两个操作数一定都在操作数栈的栈顶的两个元素中,取出这两个元素进行运算,并将运算结果再入到此栈中。
3.如果此时的运算符栈不为空,需要继续以栈顶的运算符对当前扫描运算符重复上述比较操作,以此确定是用栈顶运算符运算还是当前扫描运算符入栈。
头文件
#ifndef STACK_H//预处理器 #define STACK_H #include <iostream> using namespace std; const int maxlen = 100;//栈的最大存储量 template <typename elementType> class stack { public: stack();//构造函数,用于初始化(C++11新特性可以在类的声明中初始化变量) bool empty();//判断栈是否为空 bool full();//判断栈是否为满 bool get_top(elementType &x);//取栈顶元素 bool push(elementType x);//元素入栈 bool pop();//删除栈顶 private: int count;//元素的计数器 elementType data[maxlen];//顺序存储结构 }; template <typename elementType> stack<elementType>::stack() { count = 0; } template <typename elementType> bool stack<elementType>::empty() { if (count == 0) return true; return false; } template <typename elementType> bool stack<elementType>::full() { if (count == maxlen) return true; return false; } template <typename elementType> bool stack<elementType>::get_top(elementType &x) { if (!empty()) { x = data[count - 1]; return true; } return false; } template <typename elementType> bool stack<elementType>::push(elementType x) { if (!full()) { data[count++] = x; return true; } return false; } template <typename elementType> bool stack<elementType>::pop() { if (!empty()) { --count; return true; } return false; } #endif
源代码
#include <iostream> #include "stack.h" using namespace std; //扫描数字的函数 bool isnumber(char x) { if (x >= '0' && x <= '9') return true; return false; } //判断运算符优先级的函数 int priority(char x) { if (x == '+' || x == '-') return 0; else if (x == '*' || x == '/') return 1; else if (x == '(' || x == ')') return -1; else if (x == '#') return -2; } //运算的函数 int calculate(string s) { stack<int> number; stack<char> operate; char top; int a, b; for (unsigned int i = 0; i < s.size(); ++i) { if (isnumber(s[i])) { int Temp = 0; string temp; temp += s[i]; while (isnumber(s[++i])) temp += s[i]; for (unsigned int j = 0; j < temp.size(); ++j) { Temp = Temp * 10 + temp[j] - 48; } number.push(Temp); temp.clear(); }//将字符数字转换成整形数字 if (!isnumber(s[i])) { if (operate.empty()) { operate.push(s[i]); }//入栈第一个符号'#' else { operate.get_top(top); if (priority(s[i])>priority(top) || s[i] == '(') { operate.push(s[i]); }//入栈高优先级的运算符 else { while (priority(s[i]) <= priority(top)) { if (top == '#'&&s[i] == '#') { int answer; operate.pop(); number.get_top(answer); cout << "\n答案是:" << answer << endl; number.pop(); return 0; }//当运算符实现完全后,只剩下'#' else if (top == '('&&s[i] == ')') { ++i; }//当左右括号相遇时,跳过右括号,删除左括号 else { number.get_top(a); number.pop(); number.get_top(b); number.pop(); } if (top == '+') { b += a; number.push(b); } else if (top == '-') { b -= a; number.push(b); } else if (top == '*') { b *= a; number.push(b); } else if (top == '/') { b /= a; number.push(b); } operate.pop(); operate.get_top(top);//取前一个运算符,用于与现在扫描的运算符进行比较 }//将优先级高的运算符实现计算 operate.push(s[i]);//用于当top=='#'时,将最后一个运算符入栈 } } }//扫描运算符,并判断优先级,以及运算 }//主循环 }//对运算符的扫描,和数字字符的转化,以及计算 int main() { string expression; cout << "输入一个用'#'开头和结尾的表达式:" << endl; cin >> expression; calculate(expression); cin.get(), cin.get(); }
运行实例
相关文章推荐
- [C/C++]函数参数的入栈顺序与可变参数的实现
- C/C++函数参数的入栈顺序,计算顺序和可变参数的实现
- 顺序表求集合交并——C++实现
- C++实现动态顺序表
- c++ 实现顺序表类(初始化、输入、插入与删除)<<计算机软件技术基础 徐士良>>
- 顺序表SqList的C++代码实现
- 计算器——C++实现(CLR版本)
- 简单数据结构之顺序表(C++ 引用传递实现)
- C++类模板 实现顺序表 从《数据结构》(C++版) 北京科海摘抄
- 堆栈顺序存储的c++实现与测试
- 算式计算器C++实现代码(顺序栈结构 增加了一些功能 比如三角函数 求指教)
- 利用栈Stack实现计算器实验设计(C++)
- c++实现两个元素进栈和出栈的顺序
- 基于C++的顺序表的实现
- 《算法导论》中的查找任意顺序值的C++实现
- 数据结构——顺序队列的C++实现
- C++模板实现顺序表
- 【c++】用工厂模式实现计算器功能(附工厂模式代码)
- 约瑟夫环问题(顺序表)——C++实现
- c/c++实现顺序栈和链栈