表達式求值(牛客)

題目描述:

給定一個字符串描述的算術表達式,計算出結果值。

輸入字符串長度不超過100,合法的字符包括”+, -, *, /, (, )”,”0-9”,字符串內容的合法性及表達式語法的合法性由做題者檢查。本題目只涉及整型計算。

輸入描述:輸入算術表達式(中綴表達式)

400+5

輸出描述:計算出結果值

405

做題思路:

將輸入的中綴表達式,轉換爲對應的後綴表達式進行計算

中綴表達式:5+4*6/2+3+(4*5)/5

對應的後綴表達式:5 4 6 * 2 / 3 + 4 5 * 5 / +

中綴表達式轉爲後綴表達式:

設置一個空棧S1

1.遇到操作數直接輸出(輸出的含義是指追加到當前後綴表達式後面

2.棧爲空時,遇到運算符,直接入棧

3.遇到左括號時,直接入棧

4.遇到右括號時,如果棧頂的操作符不爲左括號,一直出棧,並將出棧的操作符輸出。當棧頂的操作符是左括號時,將左括號出棧, 停止本步驟。

5.遇到+-*/運算符op時,如果(棧非空 並且 棧頂操作符的優先級大於等於op時)一直將出棧,並將出棧的操作符輸出。當(不滿足棧非空 並且 棧頂操作符的優先級大於等於op)時,將op入棧

(棧非空 並且 棧頂操作符的優先級大於等於op時 指的是 滿足加減優先級大於等於加減,乘除優先級大於等於加減乘除的情況,其他情況均視爲不滿足)

6.將棧中所有元素以此出棧輸出

利用後綴表達式計算結果:

設置一個空棧S2

順序掃描後綴表達式S1的每一項,然後根據當前項的類型做出相應的操作

1.如果當前項是操作數:將其壓入棧S2中

2.如果當前項是操作符op:從S2彈出棧頂Y,在彈出棧頂X,計算 X<op>Y 並將結果壓入棧 S2

當S1掃描結束,S2的棧頂元素值即爲表達式的結果

注意事項:

#include<cstdlib>
string s;
int num = atoi(s.c_str());

#incldue<stack>
stack<char> s;
char c = s.top();
s.push('a');
s.pop(); //返回值是void

#include<cctype>
char c;
isdigit(c);
isalpha(c);

AC代碼:

#include<iostream>
#include<cctype>
#include<vector>
#include<stack>
#include<string>
#include<cstdlib>

using namespace std;

bool Cmppriority(char s,char c); //比較操作符的優先級
vector<string> sTrans(string &str);//將中綴表達式轉換爲後綴表達式 
int Calculate(vector<string> res);//根據後綴表達式計算結果
 
int main()
{
	string str;
	cin >> str;
	
	vector<string> res = sTrans(str); 
	int result = Calculate(res);
	
	cout<<result<<endl;
	
	return 0;
} 

bool Cmppriority(char s,char c)
{
	if( (c=='*'||c=='/')&&(s=='*'||s=='/') ){
		return true;
	}
	if( (c=='+'||c=='-')&&(s=='+'||s=='-'||s=='*'||s=='/')){
		return true;
	}
	return false;
}
vector<string> sTrans(string &str)
{
	vector<string> result; //記錄後綴表達式 
	stack<char> s;  //用作中間棧,調整符號在後綴表達式中的位置
	string temp; 
	
	for(int i=0; i<str.size(); i++){
		if( isdigit(str[i]) ){  //是一個操作數 
			temp="";
			while( i<str.size()&&isdigit(str[i]) ){
				temp += str[i];
				++i;
			}  
			i--;
			result.push_back(temp); //如果是操作符直接入棧到result
		}else{  //是一個操作符 
			if( s.empty() ){  //棧爲空時操作符直接入棧到stack  
				s.push(str[i]);
			}else{
				if( str[i]=='(' ){
					s.push(str[i]);
				}else{
					if( str[i]==')' ){
						while( s.top()!='(' ){
							temp = "";
							temp += s.top();
							result.push_back(temp); //stack出棧 並 入棧到後綴表達式 
							s.pop();
						}
						s.pop(); //將左括號出棧 
					}else{  //遇到+-*/ 
						while( !s.empty()&&Cmppriority(s.top(),str[i]) ){
							temp = "";
							temp += s.top();
							result.push_back(temp);
							s.pop();
						}
						s.push(str[i]);
					}
				}
			}
		} 
	} 
	while( !s.empty() ){
		temp = "";
		temp += s.top();
		result.push_back(temp);
		s.pop();
	}
	return result; 
}
int Calculate(vector<string> res)
{
	stack<int> result;
	for(int i=0; i<res.size(); i++){
		if( isdigit(res[i][0]) ){ //是操作數 
			result.push(atoi(res[i].c_str())); 
		}else{
			int B = result.top();
			result.pop();
			int A = result.top();
			result.pop();
			
			if( res[i]=="+" ){
				result.push(A+B);
			}
			if( res[i]=="-" ){
				result.push(A-B);
			}
			if( res[i]=="*" ){
				result.push(A*B);
			}
			if( res[i]=="/" ){
				result.push(A/B);
			}
		}
	}
	return result.top();
} 

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章