In: Computer Science
The N-QUEENS PROBLEM
Given a chess board having N x N cells, we need to place N queens in such a way that no queen is attacked by any other queen. A queen can only attack horizontally, vertically and diagonally.
Let’s go at this one step at a time.
let’s place the first Queen at some cell, (I, j) and now the number of unattackable cells are reduced. And now, the number of the Queens to be placed are N – 1.
Now place the next queen at some unattacked cell and this reduces the number of unattacked cells and number of queens to be placed becomes N – 1. You can continue doing this as long as the following conditions hold:
The number of unattacked cells is not 0
The number of queens to be placed is not 0
If the number of Queens placed becomes 0, then we found a solution, but if the number of unattacked cells become 0, then we need to backtrack, i.e., move the last placed queen from its current cell, and place it at some other cell. We can do this recursively. Let’s try this for an N = 4
What did you figure out?
What is the input for this problem?
What is the Output for this problem?
If it is possible to place all N Queens so that no Queen attacks another Queen.
If it is not possible to place all N Queens so that no Queen attacks another Queen.
Yes, the following configuration is possible in a 4 x 4 matrix.
The value 1 indicates the presence of queens.
0 0 1 0 1 0 0 0 0 0 0 1 0 1 0 0
Following is a c/c++ code :
define N 4
#include <stdbool.h>
#include <stdio.h>
/* A utility function to print solution */
void
printSolution(
int
board[N][N])
{
for
(
int
i = 0; i < N; i++)
{
for
(
int
j = 0; j < N;
j++)
printf
(
"
%d "
, board[i][j]);
printf
(
"\n"
);
}
}
/* A utility function to check if a queen can
be placed on
board[row][col]. Note that this
function is called when
"col" queens are
already placed in columns
from 0 to col -1.
So we need to check only
left side for
attacking queens
*/
bool
isSafe(
int
board[N][N],
int
row,
int
col)
{
int
i,
j;
/* Check this row on
left side */
for
(i =
0; i < col; i++)
if
(board[row][i])
return
false
;
/* Check upper
diagonal on left side */
for
(i =
row, j = col; i >= 0 && j >= 0; i--, j--)
if
(board[i][j])
return
false
;
/* Check lower
diagonal on left side */
for
(i =
row, j = col; j >= 0 && i < N; i++, j--)
if
(board[i][j])
return
false
;
return
true
;
}
/* A recursive utility function to solve N
Queen problem */
bool
solveNQUtil(
int
board[N][N],
int
col)
{
/* base case: If all
queens are placed
then
return true */
if
(col
>= N)
return
true
;
/* Consider this
column and try placing
this
queen in all rows one by one */
for
(
int
i = 0; i < N; i++)
{
/*
Check if the queen can be placed on
board[i][col]
*/
if
(isSafe(board, i, col)) {
/*
Place this queen in board[i][col] */
board[i][col]
= 1;
/*
recur to place rest of the queens */
if
(solveNQUtil(board, col + 1))
return
true
;
/*
If placing queen in board[i][col]
doesn't
lead to a solution, then
remove
queen from board[i][col] */
board[i][col]
= 0;
// BACKTRACK
}
}
/* If the queen
cannot be placed in any row in
this
colum col then return false */
return
false
;
}
/* This function solves the N Queen problem
using
Backtracking. It mainly
uses solveNQUtil() to
solve the problem. It
returns false if queens
cannot be placed,
otherwise, return true and
prints placement of queens
in the form of 1s.
Please note that there may
be more than one
solutions, this function
prints one of the
feasible
solutions.*/
bool
solveNQ()
{
int
board[N][N] = { { 0, 0, 0, 0 },
{
0, 0, 0, 0 },
{
0, 0, 0, 0 },
{
0, 0, 0, 0 } };
if
(solveNQUtil(board, 0) ==
false
)
{
printf
(
"Solution
does not exist"
);
return
false
;
}
printSolution(board);
return
true
;
}
// driver program to test above function
int
main()
{
solveNQ();
return
0;
}
The input and output are given above. Input is taken in
the code and output is:
0 0 1 0 1 0 0 0 0 0 0 1 0 1 0 0
Here, 1 indicates the presence of queens.