oj -栈的运用2-简单计算器

在这里插入图片描述
解法细节说明:
分析:这一算式用str保存,然后用op和in两个栈存运算符和数,数可以是中途加减操作过的数。
编写一个判断数字还是操作符的函数,在起始时顺便返回标记,以便下面一操作。
op栈在入栈的时候,函数判断过之后,注意对起始位置的入栈。
这时要说一下运算级别,就是优先级,首先,标识符在左,则任何的运算符都大于它,反之一样,以0 1234代表起始和4个基本操作。即:
1 0 0 0 0
1 0 0 0 0
1 0 0 0 0
1 1 1 0 0
1 1 1 0 0 值得注意的细节是,0,0位置的数,请看: (6+8+9)这时候第二个加法一定要比第一个加法优先级小,然后让前面两个6+8算出来,而如果是()两个起始的比较,)一定要比(的优先级大才可以存入,以便结束的判断。
之后看数字就入栈,是运算符时栈为空,或者优先级大就存栈,或者结束。
在这里插入图片描述

#include<stdio.h>
#include<iostream>
#include<stack>

using namespace std;

char str[100]; 
int mat[5][5] = {
1,0,0,0,0,
1,0,0,0,0,
1,0,0,0,0,
1,1,1,0,0,
1,1,1,0,0,
};
stack<int>op;
stack<double> in;
void get(bool &o,int &n,int &i){
	if(i == 0 && op.empty() == true)
	{
		o = true;
		n = 0;
		return;
	}
	if(str[i] == 0){
		o = true;
		n = 0;
		return;
	}
	if(str[i]>='0'&&str[i]<='9'){
		o = false;
	}
	else{
		o = true;
		if(str[i]=='+') n = 1;
		if(str[i]=='-') n = 2;
		if(str[i]=='*') n = 3;
		if(str[i]=='/') n = 4;

		i+=2;//跳过空格 
		return;
	}
	n = 0;
	for(;str[i]!=' '&&str[i]!=0;i++){
		n*=10;
		n+=str[i] - '0';
	}
	if(str[i]==' ')
		i++;//弥补数字判断没有对空格的跳跃++
	return; 
}
int main(){ 
	while(gets(str)){
		if(str[0]=='0'&&str[1]==0) break;
		bool stro;
		int strn;
		int i = 0;
		while(!op.empty()) op.pop();
		while(!in.empty()) in.pop();
		while(true){
			get(stro,strn,i);//i很重要,要传入去,函数为局部变量
			if(stro == false) in.push((double)strn);
			else{//这一位为操作符 
				double tmp;
				if(op.empty()==true||mat[strn][op.top()] == 1){
					op.push(strn);//不计算算数 
				}
				else{//操作符的优先级小与栈内,立马运算 
					while(mat[stro][op.top()]==0)//一直算到起始,优先级最小,即操作符的优先级大于栈内
					{
						int top = op.top();
						op.pop();
						double b = in.top();
						in.pop();
						double a = in.top();
						in.pop();
						if(top==1) tmp = a+b;
						else if(top==2) tmp = a-b;
						else if(top==3) tmp = a*b;
						else if(top==4) tmp = a/b;
						in.push(tmp);
					}//算完,记得存新运算符 
					op.push(strn);
				}
			}
			if(op.size()==2&&op.top()==0) break;
		}
		cout<<in.top()<<endl;
	}
}

这代码量难以想象在半小时内竟然可以完成,总有些小细节忘记,还是先把草稿打好再写为妙。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值