八皇后(c 啟發式函式求解)

2022-09-04 07:42:07 字數 2241 閱讀 7592

八皇后問題是回溯演算法的典型案例,在回溯法中,常常是盲目搜尋,耗費過多的搜尋時間。在本次實驗中,使用了啟發式搜尋,搜尋時不是任取乙個分支,而是選擇最佳的分支往下搜尋。通過定義狀態空間、操作規則、搜尋策略,我們可以清晰快速地得到原問題的乙個解。

八皇后問題是乙個以西洋棋為背景的問題:如何能夠在 8×8 的西洋棋棋盤上放置八個皇后,使得任何乙個皇后都無法直接吃掉其他的皇后?為了達到此目的,任兩個皇后都不能處於同一條橫行、縱行或斜線上。通過計算機程式設計,我們可以快速地求出問題的解。

(i,c[i]), i = 0,1,…,7;

(i,c[i])表示第i行的皇后放置在第c[i]列。

初始狀態為c[i] = -1, i = 0,1,…,7;表示所有行都不放置皇后。

目標狀態為c[i] != -1, i = 0,1,…,7;表示所有行都已經放置了皇后。

第乙個皇后放在第一行;

第二個皇后放在第二行且不與第乙個皇后在同一列或對角線的空格上;

……第i個皇后放在第i行且不與前面i-1個皇后在同一列或對角線的空格上。

由於在某一步放置某個皇后時,可能有多個空格可以使用,所以定義啟發式函式:

fx = 剩下未放行中能夠用來放皇后的空格數

如果第i行的皇后放在第j列合法,計算啟發式函式的值fx(i,j)。計算出第i行所有空格的fx後,將第i個皇后放到第i行中那個與前面i-1個皇后不在同一列或對角線上且fx值最大的空格中(相同時取第乙個)。

如果當前策略無法求解,則回溯至上一步,選擇fx值次大的空格放置皇后,依次類推,直至找到乙個合法的解。

#include#include 

#include

#include

#include

#include

#include

#include

#include

#include

#include

#include

#include

#include

using

namespace

std;

const

int n=8

;int c[8]; //

c[i]表示第i行的皇后放在第c[i]列

int fx[8][8]; //

fx[i][j]表示在i行j列放置皇后後,剩下行中可以放q的空格數

int ansflag=0; //

標記是否已經找到答案

int vis[3][16]; //

vis[0][j]表示第j列有無皇后,vis[1][i+j]表示對角線/上的和相同),vis[2][i-j+n]表示對角線\上的差相同,+n避免負數

//啟發式函式f():找到剩下行可以放q的空格數

int f(int

row)

}return

cnt;

}void search(int

cur)

}if(flag) //

標誌該行可以放置皇后

}if(max==-1) //

在本行任一空格放置皇后都無法求解,回溯

c[cur]=col; //

找到fx最大的列,放置皇后,搜尋下一行。

vis[0][col]=vis[1][cur+col]=vis[2][cur-col+n]=1

; search(cur+1

); vis[

0][col]=vis[1][cur+col]=vis[2][cur-col+n]=0

; }

}else

//標誌該行不可以放置皇后

fx[cur-1][c[cur-1]]=-1

; }

}int

main()

cout

<}

}

解對應的棋盤: 

q x x x x x x x 

x x x x x q x x 

x x x x x x x q 

x x q x x x x x 

x x x x x x q x 

x x x q x x x x 

x q x x x x x x 

x x x x q x x x

DFS和啟發式求解八皇后問題 Python

coding utf 8 import numpy as np class eightqueens def init self self.board np.ones 8,8 解的數量 self.counter 0 當前已經放置的棋子 self.chess puted 儲存選中當前行每列 m,n 中棋...

啟發式搜尋之八皇后問題

主要公式fx gx hx g x 針對於初始節點,到目標節點實際所需要付出的帶價 h x 針對初始節點,到目標節點所需要的估計帶價 在八皇后問題上,估計帶價,是自己預定的,此處設定,其為皇后的碰撞對數,當然,估計是最優 的問題,就是0,無碰撞才是最優的結果。注釋都有,自行消化 package heu...

八數碼問題 啟發式搜尋

一 問題描述 在乙個3 3 的方棋盤上放置著 1,2,3,4,5,6,7,8 八個數碼 每個數碼佔一格 且有乙個空格。這些數碼可以在棋盤上移動,其移動規則是 與空格相鄰的數碼方格可以移入空格。現在的問題是 對於指定的初始棋局和目標棋局,給出數碼的移動序列。該問題稱八數碼難題或者重排九宮問題。原始碼 ...