经典回溯算法 八皇后 解法

经典回溯算法 八皇后 解法

八皇后问题,是一个古老而著名的问题,是回溯算法的典型案例。该问题是国际西洋棋棋手马克斯·贝瑟尔于1848年提出:在8×8格的国际象棋上摆放八个皇后,使其不能互相攻击,即任意两个皇后都不能处于同一行、同一列或同一斜线上,问有多少种摆法。

回溯法又称作动态穷举法。下面来看一下具体的实现思路。

一个皇后的具体位置必须满足以下条件:

  1. 该皇后所在行没有其它皇后
  2. 该皇后的所在列没有其它皇后
  3. 该皇后所在的对角线没有其它皇后(这里的对角线分为正对角线和反对角线)

满足以上三个条件。那么我们可以说这个皇后的位置正确

可以先看看思路
现有一个8x8的棋盘,但是下标从0开始。于是第一个皇后可以直接站在(0,0)的位置。第二个皇后选取位置的时候,(1,0)已经不行了,因为在0列上已经有第一个皇后了。选取第二个位置(1,1),也是不行的,处于第二个皇后的对角线上,选取第三个位置(1,2),没有问题。选取第n个皇后的位置判定失败,那么就回溯上一级,重新调整位置。

下面给出具体实现(js描述)

//皇后容器
let queenArr = []
//皇后的个数
const QUEEN_COUNT = 8
//解法的个数
let sum = 0

//初始化皇后
function initqueen(){
    for(let i = 0;i < QUEEN_COUNT;i++){
        queenArr.push({
            row:-1,
            column:-1
        })
    }
}

//判断皇后当前位置是否合法
function isRight(row, column){
    let currentqueen
    for(let r = 0;r < row;r++) {
        currentqueen = queenArr[r]
        if( 
            //是否处于同一列
            currentqueen.column == column ||
            //是否处于同一正对角线
            (currentqueen.column + currentqueen.row) == (row + column) || 
            //是否处于同一负对角线
            (currentqueen.column - currentqueen.row) == (column - row)
        ) return false
    }
    return true
}

//匹配皇后的位置
function matchqueen(row){
    for(let column = 0;column < QUEEN_COUNT;column++){
        //判断当前位置是否合法
        if(isRight(row, column)) {
            queenArr[row].row = row
            queenArr[row].column = column
            // 是否达到最后一行
            if(row == 7) {
                sum++
                printDiagram()
                return
            }
            matchqueen(row + 1)
        }
    }
}

//创建图
function createDiagram(){
    let diagram = []
    for(let i = 0;i < QUEEN_COUNT;i++){
        diagram.push([])
        for(let j = 0;j < QUEEN_COUNT;j++) {
            diagram[i][j] =  0
        }
    }
    return diagram
}

//输出图
function printDiagram(){
    let diagram = createDiagram()
    for(let i = 0;i < QUEEN_COUNT;i++){
        diagram[queenArr[i].row][queenArr[i].column] = 1
    }
    console.log(diagram)
    console.log("\n")
}

initqueen()
matchqueen(0)


console.log(sum)

这里写图片描述

猜你喜欢

转载自blog.csdn.net/haodawang/article/details/80413404