CCF試題 201903-2 二十四點

題目描述

這道題目的主要解題思想是用堆棧來解決四則運算的優先級問題。
在這裏插入圖片描述
在這裏插入圖片描述
本題的關鍵點在於如何正確處理運算符的優先級問題,可以使用兩個棧來解決這個問題。一個是運算數棧,另一個是運算符棧。

在遍歷當前算術表達式字符串時會有五種情況:

  1. 當前字符是數字。
    如果當前字符是數字的話,那麼就直接將其轉換成對應的整型數並壓入運算數棧中。
  2. 當前字符是加號
    由於加法的優先級低於乘法和除法,所以不能直接進行加法運算,要先把加號壓入運算符棧中。
  3. 當前字符是減號
    減法的優先級同加法一樣,也不能直接進行運算。此處爲了後續操作方便,統一將a-b的形式轉換成a+(-b)的形式來運算減法。即將加號壓入運算符棧中,將第二個運算數取反之後壓入運算數棧中。
  4. 當前字符是乘號
    乘法在本題中是優先級最高的,可以直接進行運算。去運算數棧的棧頂元素和乘號後面的那個運算數做乘法,將結果再壓入運算數棧中。
  5. 當前字符是除號
    除法的優先級同乘法一樣,操作同上。

在遍歷完算術表達式時,說明式子中的乘除運算都已經完成,下面只剩下加法(減法已經轉換成加法),直到運算符棧爲空,最終的結果就是運算數的棧頂元素。最後拿這個數和24來進行比對即可。

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

using namespace std;

//二十四點遊戲 ,特別注意運算符的優先級問題!!!用堆棧來解決 
int main() {
	int n; //表達式的個數 
	string str; //暫存當前表達式 
	int i, j;
	int result[100] = {0}; //1代表計算結果是24, 0代表不是 
	stack<int> num; //運算數棧 
	stack<char> op; //運算符棧 
	
	cin >> n;
	for (i = 0; i < n; i++) {
		cin >> str;
		for (j = 0; j < str.length(); j++) {
			if (isdigit(str[j])) { //是數字 
				num.push(str[j] - '0');
			} else if (str[j] == '+') {
				op.push('+');
			} else if (str[j] == '-') { //將減法轉換成加法 
				op.push('+');
				num.push(-(str[j + 1] - '0'));
				j++;
			} else if (str[j] == 'x') { //直接計算乘法 
				int num1 = num.top();
				num.pop();
				num.push(num1 * (str[j + 1] - '0'));
				j++;
			} else if (str[j] == '/') { //直接計算除法 
				int num1 = num.top();
				num.pop();
				num.push(num1 / (str[j + 1] - '0'));
				j++;
			}
		}
		while (!op.empty()) {
			int num1 = num.top();
			num.pop();
			int num2 = num.top();
			num.pop();
			num.push(num1 + num2);
			op.pop();
		}
		if (num.top() == 24) {
			result[i] = 1;
		}
		num.pop(); //清空操作數棧	
	}
	for (i = 0; i < n; i++) {
		if (result[i] == 0) {
			cout << "No" << endl;
		} else {
			cout << "Yes" << endl;
		}
	}
	return 0;
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章