八皇后問題的遞迴求解

2021-07-05 03:18:07 字數 2470 閱讀 9894

**:

1.引子

中國有一句古話,叫做「不撞南牆不回頭」,生動的說明了乙個人的固執,有點貶義,但是在軟體程式設計中,這種思路確是一種解決問題最簡單的演算法,它通過一種類似於蠻幹的思路,一步一步地往前走,每走一步都更靠近目標結果一些,直到遇到障礙物,我們才考慮往回走。然後再繼續嘗試向前。通過這樣的波浪式前進方法,最終達到目的地。當然整個過程需要很多往返,這樣的前進方式,效率比較低下。

2.適用範圍

適用於那些不存在簡明的數學模型以闡明問題的本質,或者存在數學模型,但是難於實現的問題。

3.應用場景

在8*8西洋棋棋盤上,要求在每一行放置乙個皇后,且能做到在豎方向,斜方向都沒有衝突。西洋棋的棋盤如下圖所示:

3c3f32555ed870c1b745aeb2

4.分析

基本思路如上面分析一致,我們採用逐步試探的方式,先從乙個方向往前走,能進則進,不能進則退,嘗試另外的路徑。首先我們來分析一下西洋棋的規則,這些規則能夠限制我們的前進,也就是我們前進途中的障礙物。乙個皇后q(x,y)能被滿足以下條件的皇后q(row,col)吃掉

1)x=row(在縱向不能有兩個皇后)

2) y=col(橫向)

3)col + row = y+x;(斜向正方向)

4) col - row = y-x;(斜向反方向)

遇到上述問題之一的時候,說明我們已經遇到了障礙,不能繼續向前了。我們需要退回來,嘗試其他路徑。

我們將棋盤看作是乙個8*8的陣列,這樣可以使用一種蠻幹的思路去解決這個問題,這樣我們就是在8*8=64個格仔中取出8個的組合,c(64,80) = 4426165368,顯然這個數非常大,在蠻幹的基礎上我們可以增加回溯,從第0列開始,我們逐列進行,從第0行到第7行找到乙個不受任何已經現有皇后攻擊的位置,而第五列,我們會發現找不到皇后的安全位置了,前面四列的擺放如下:

image

第五列的時候,擺放任何行都會上圖所示已經存在的皇后的攻擊,這時候我們認為我們撞了南牆了,是回頭的時候了,我們後退一列,將原來擺放在第四列的皇后(3,4)拿走,從(3,4)這個位置開始,我們再第四列中尋找下乙個安全位置為(7,4),再繼續到第五列,發現第五列仍然沒有安全位置,回溯到第四列,此時第四列也是乙個死胡同了,我們再回溯到第三列,這樣前進幾步,回退一步,最終直到在第8列上找到乙個安全位置(成功)或者第一列已經是死胡同,但是第8列仍然沒有找到安全位置為止

總結一下,用回溯的方法解決8皇后問題的步驟為:

1)從第一列開始,為皇后找到安全位置,然後跳到下一列

2)如果在第n列出現死胡同,如果該列為第一列,棋局失敗,否則後退到上一列,在進行回溯

3)如果在第8列上找到了安全位置,則棋局成功。

8個皇后都找到了安全位置代表棋局的成功,用乙個長度為8的整數陣列queenlist代表成功擺放的8個皇后,陣列索引代表棋盤的col向量,而陣列的值為棋盤的row向

量,所以(row,col)的皇后可以表示為(queenlist[col],col),如上圖中的幾個皇后可表示為:

queenlist[0] = 0; queenlist[1] = 3; queenlist[2] = 1; queenlist[3] = 4; queenlist = 2;

我們看一下如何設計程式:

首先判斷(row,col)是否是安全位置的演算法:

bool issafe(int col,int row,int queenlist)

if (tempcol == col)

if (temprow - tempcol == row - col || temprow + tempcol == row + col)

}return

true;

}

設定乙個函式,用於查詢col列後的皇后擺放方法:

///

/// 在第col列尋找安全的row值

//////

//////

public

bool

placequeue(int queenlist, int col)

else

}else}}

return foundsafepos;

}

呼叫方法:

static

void main(string args)

console.writeline("");

for (int i = 0; i < 8; i++)

else

}console.writeline("");

}console.writeline("---------------------------------------");

}else

}console.read();

}

遞迴演算法placequeue,完成這樣的功能:它尋找第col列後的皇后的安全擺放位置,如果該函式返回了false,表示當前進入了死胡同,需要進行回溯,直到為0-7列都找

到了安全位置或者找遍這些列都找不到安全位置的時候終止。

八皇后問題 遞迴求解

八皇后問題簡述 在西洋棋中,皇后是最厲害的 這也就是大概為什麼不要得罪女人的原因 她可以吃掉任意與其所在列和行,以及對角線上的棋子。所以在8x8的棋盤上,安放8個皇后,使得不會相互攻擊,也就是安全的就變得極為重要。本文採用遞迴的方式,輸出所有的92種可能的方法。如下 include stdafx.h...

八皇后問題 遞迴求解

在西洋棋的棋盤上,按照西洋棋的規則,擺放8個皇后,使之 和平共處 如圖所示,在3 d上有乙個皇后,則綠色區域中都不能再放置皇后了。最暴力的方法就是使用八個for,但是很明顯,這種方法效率太低。對於放置了皇后的位置,仔細觀察棋盤可以發現每一列 行 只能有乙個皇后,每乙個主 次 對角線上也只能有乙個皇后...

遞迴求解八皇后問題

題目 八皇后問題 在8 8格的西洋棋上擺放八個皇后,使其不能互相攻擊,即任意兩個皇后都不能處於同一行 同一列或同一斜線上,問有多少種擺法 遞迴思路 在第1行安全位置放乙個棋子,在第2行安全位置放乙個棋子,以此類推,直到八行都放了棋子,第9行時退出遞迴過程。c 八皇后問題 在8 8格的西洋棋上擺放八個...