c/c++演算法之“24點”經典問題
阿新 • • 發佈:2019-02-01
24點遊戲是一種使用撲克牌來進行的益智類遊戲,遊戲內容是:從一副撲克牌中抽去大小王剩下52張,任意抽取4張牌,把牌面上的數(A代表1)運用加、減、乘、除和括號進行運算得出24。每張牌都必須使用一次,但不能重複使用。 有些組合有不同種演算法,例如要用2,4,6,12四張牌組合成24點,可以有如下幾種組合方法: 2 + 4 + 6 + 12 = 24 4 × 6 ÷ 2 + 12 = 24 12 ÷ 4 × (6 + 2) = 24 當然,也有些組合算不出24,如1、1、1、1 和 6、7、8、8等組合。”
本演算法的實習過程是通過你迴圈迭代實現24點的判斷,實現過程是以紙牌的張數作為迴圈的中樞,也即本演算法的擴充套件性較強,可以實現的不只是抽取4張牌,5張,6張等都一樣都能實現。
下面以n張牌為例,敘述該演算法。
第一步:抽取n張牌當中的任意兩張牌,對其做加減乘除運算,將這兩個數四則運算過後的結果作為一個數,與其餘n-2個數一起構成n-1個數據。
第二步:將得到的n-1組資料,重複第一步的操作。
一二步不斷迴圈,直到n=1,這個時候所有的可能全部計算完畢,輸出結果。
程式碼如下:
#include<iostream> #include<string> #include<cmath> using namespace std; const double PRECISION = 1E-6; const int COUNT = 4; const int RESULT = 24; double number[COUNT]; //這裡一定要用double,看看第一題的答案就知道為什麼了 string expression[COUNT]; //儲存表示式 bool Test(int n) { //遞迴結束 if (n == 1) { if (fabs(number[0] - RESULT) < PRECISION) { cout << expression[0] << endl; return true; } else return false; } //遞迴過程 for (int i = 0; i < n; i++) { for (int j = i + 1; j < n; j++) { double a, b; string expa, expb; a = number[i]; b = number[j]; number[j] = number[n - 1]; expa = expression[i]; expb = expression[j]; expression[j] = expression[n - 1]; expression[i] = '(' + expa + '+' + expb + ')'; number[i] = a + b; if (Test(n - 1)) return true; //減號有兩種情況,a-b與b-a expression[i] = '(' + expa + '-' + expb + ')'; number[i] = a - b; if (Test(n - 1)) return true; expression[i] = '(' + expb + '-' + expa + ')'; number[i] = b - a; if (Test(n - 1)) return true; expression[i] = '(' + expa + '*' + expb + ')'; number[i] = a * b; if (Test(n - 1)) return true; //除法也有兩種情況,a/b與b/a if (b != 0) { expression[i] = '(' + expa + '/' + expb + ')'; number[i] = a / b; if (Test(n - 1)) return true; } if (a != 0) { expression[i] = '(' + expb + '/' + expa + ')'; number[i] = b / a; if (Test(n - 1)) return true; } //恢復陣列 number[i] = a; number[j] = b; expression[i] = expa; expression[j] = expb; } } return false; } int main(void) { for (int i = 0; i < COUNT; i++) { char buffer[20]; int x; cin >> x; number[i] = x; itoa(x, buffer, 10); expression[i] = buffer; } if (Test(COUNT)) cout << "Success" << endl; else cout << "Fail" << endl; system("pause"); return 0; }
如有疑問,歡迎交流