[C++]栈(数组描述)& 利用栈实现一位整数计算器

定义栈类

template<class T>
class arrayStack//自定义数组描述的栈类
{
public:
	arrayStack(int init=100)//栈初始化
	{
		arrayLength = init;
		arr = new T[arrayLength];
		stackTop = -1;
	}

	~arrayStack() {delete[]arr;}

	bool empty()const {return stackTop == -1;}

	int size() {return stackTop + 1;}

	T& top() {return arr[stackTop];}

	//出栈
	void pop() { arr[stackTop].~T(); stackTop--; }

	//进栈
	void push(const T& theElement)
	{
		if (stackTop == arrayLength - 1)//空间已满容量加倍
		{
			T* temp = new T[2 * arrayLength];
			for (int i = 0; i <= stackTop; i++)
			{
				temp[i] = arr[i];
			}
			delete[]arr;
			arr = temp;
			delete[]temp;
			arrayLength *= 2;
		}
		arr[++stackTop] = theElement;
	}
private:
	int arrayLength;//栈容量
	int stackTop;//栈顶位置
	T* arr;//栈的数组表示
};

计算器

对于一个有括号的加减乘除混合运算式字符串,对其的处理过程分为两步:
1.利用栈将中缀式化为后缀式,从而去除括号并且确定运算顺序。
2.利用栈计算后缀式。

中缀式->后缀式

string changeString(string& str)//中缀表达式转换为后缀表达式
{
	string newStr = "";//后缀表达式
	arrayStack<string> stack;//临时存放符号的栈
	for (int i = 0; i < str.length(); i++)//遍历中缀式每个字符
	{
		string c = str.substr(i, 1);
		if (c == "0" || c == "1" || c == "2" || c == "3" || c == "4" || c == "5" || c == "6" || c == "7" || c == "8" || c == "9")//数字:直接进入后缀式
		{
			newStr = newStr + c;
		}
		else if (c == "(")//左括号:直接进栈
		{
			stack.push(c);
		}
		else if (c == ")")//右括号:把左括号之前的所有符号全部出栈加进后缀式中,然后删除左括号
		{
			while (stack.top() != "(")
			{
				newStr = newStr + stack.top();
				stack.pop();
			}
			stack.pop();
		}
		else if (c == "*" || c == "/")//乘除号:先让栈顶的乘除号出栈,然后自己进栈
		{
			while ((!stack.empty()) && (stack.top()=="*"|| stack.top() == "/"))
			{
				newStr = newStr + stack.top();
				stack.pop();
			}
			stack.push(c);
		}
		else if (c == "+" || c == "-")//加减号:让左括号之前的所有符号出栈,然后自己进栈
		{
			while ((!stack.empty()) && stack.top() != "(")
			{
				newStr = newStr + stack.top();
				stack.pop();
			}
			stack.push(c);
		}
	}
	while (!stack.empty())//遍历完中缀式之后,让栈中剩余符号全部出栈
	{
		newStr = newStr + stack.top();
		stack.pop();
	}
	return newStr;
}

计算后缀式

void calculate(string& str)//传入后缀式
{
	arrayStack<double> stack;//用于临时存放数字
	for (int i = 0; i < str.length(); i++)
	{
		string c = str.substr(i, 1);
		if (c == "0" || c == "1" || c == "2" || c == "3" || c == "4" || c == "5" || c == "6" || c == "7" || c == "8" || c == "9")//数字:直接进栈
		{
			//利用流将字符串转为数字
			stringstream ss(c);
			double num;
			ss >> num;
			stack.push(num);
		}
		else if (c == "+" || c == "-" || c == "*" || c == "/")//符号:取出栈顶的两个数字进行运算,将运算结果压入栈中
		{
			double a = stack.top();
			stack.pop();
			double b = stack.top();
			stack.pop();
			if (c == "+")
			{
				b += a;
			}
			else if (c == "-")
			{
				b -= a;
			}
			else if (c == "*")
			{
				b *= a;
			}
			else if (c == "/")
			{
				if (a == 0)
				{
					cout << "除数不应为零!" << endl;
				}
				else 
				{
					double c = (double)b / (double)a;
					b = c;
				}
			}
			stack.push(b);
		}
	}
	//后缀式遍历完之后,栈顶数字即为运算结果
	//由于涉及除法,于是决定将结果保留两位小数
	printf("%0.2f\n", stack.top());
}
  • 0
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值