首先要總結出8*8棋盤中從左上到右下斜線的座標關係,假設現在座標是(1,1),(2,2),…,(i,j),…,(8,8),你會發現i-j的差為0,將這個i與j相減擴散到整個棋盤,會得到下面這張圖,及i-j的結果範圍是[-7,7],i-j+7的結果範圍就是[0,14].
其次,再考慮棋盤中從左下到右上斜線的座標關係,假設現在座標是(1,8),(2,7),(3,6),…,(i,j),…,(7,2),(8,1),你會發現有(1,8),(8,1)以及(2,7),(7,2)這類數字出現,兩個數顛倒下位置,不過這哥倆的總和是不變的,即i+j=固定數,那這個固定的數範圍是[2,16],將i和j相加,會得到下圖
上文可以理解後,接下來思考如何擺放皇后娘娘,因為要確保每行每列每左右斜線都只能有乙個皇后,棋盤大小一共8行8列。於是
第一步、宣告標記陣列:
row[9] 行陣列(因為有8行,陣列第乙個下標是0,所以要宣告大小為9)
col[9] 列陣列(因為有8列,陣列第乙個下標是0,所以要宣告大小為9)
leftslash[17] 左斜線陣列(因為i-j+7最大是14,這裡宣告大一些到17)
rightslash[17] 右斜線陣列(因為i+j最大會到16,陣列第乙個下標是0,所以要宣告大小為17)
第二步、從第一行開始深搜,滿足這一行,這一列,這一左斜線,這一右斜線只有乙個1,就將皇后放在該位置上
第三步,如果按照這種方法擺放,已經放了8行的皇后,則輸出現在的8*8棋盤,否則繼續下一行
最後一步,深搜精髓之回溯,因為深搜是只要當前點滿足當前的條件,就一路走到黑,不成功便成仁,最壞的情況就是萬一從這一點往下放皇后,放不滿8個皇后,則之前走過的錯路,一定要回溯,就是講原來置成1的要重置回0.
至此,借助深搜輸出的八皇后方案,一共92種,這個數字要當做常識記住哦,全部**:
#includeusing namespace std;
//為了省事,統一陣列大小都是20
const int n=20;
//int row[n];
int a[n][n],col[n],leftslash[n],rightslash[n],ans=0;
void printmatrix()else
cout<
} puts(""); }}
//現在要放置第x行的皇后
void dfs(int x)else
//回溯
col[j]=0;
a[x][j]=0;
leftslash[x+j]=0;
rightslash[x-j+7]=0;
} }}int main()
資訊學奧賽一本通 1214 八皇后
時間限制 1000 ms 記憶體限制 65536 kb 提交數 2702 通過數 1636 會下西洋棋的人都很清楚 皇后可以在橫 豎 斜線上不限步數地吃掉其他棋子。如何將8個皇后放在棋盤上 有8 8個方格 使它們誰也不能被吃掉!這就是著名的八皇后問題。對於某個滿足要求的8皇后的擺放方法,定義乙個皇后...
《資訊學奧賽一本通》 位數問題 題解
時間限制 1000 ms 記憶體限制 65536 kb 提交數 3907 通過數 2025 在所有的n n位數中,有多少個數中有偶數個數字3 3 由於結果可能很大,你只需要輸出這個答案對12345 12345 取餘的值。讀入乙個數n n 1000 n n 1000 輸出有多少個數中有偶數個數字3 3...
資訊學奧賽一本通提高篇題解
感謝齊工大oj提供測試環境 1.1 貪心 活動安排 區間貪心,對於區間,按照右端點公升序排序,然後選擇離前乙個區間最近的不重合區間 種樹 對於區間,按照右端點公升序排序,讓樹盡量種在靠右的地方,用陣列標記狀態 噴水裝置 1.2 二分 憤怒的牛 最小值最大,二分距離mid 對於mid,如果距離大於mi...