1. 程式人生 > >遞迴求解N皇后問題

遞迴求解N皇后問題

#include<stdio.h>
#define Debug
int count=0;
void Queen(int n,int l);
bool CanPut(int i,int j,int (*a)[8],int n);
void Print(int (*a)[8],int n);

int main()
{
	printf("請輸入棋盤的規模\n");
	int n;
	scanf("%d",&n);

	Queen(n,0);
	if(count)
		printf("解的總數是:%d\n",count);
	else
		printf("無解\n");

	return 1;
}

int a[8][8]={0};

void Queen(int n,int l)
{
	if(l==n-1)//最後一行,遞迴出口
	{
		for(int j=0;j<n;j++)
		{
			if(CanPut(l,j,a,n))//是否能放置皇后
			{
				count++;
				a[l][j]=1;//標記位置
				Print(a,n);
				a[l][j]=0;//取消這個位置
			}
		}
		printf("\n");
	}
	else//不是最後一行
	{
		for(int j=0;j<n;j++)
		{
			a[l][j]=1;//假設這個位置可以放
			if(CanPut(l,j,a,n))//如果可以,遞迴進入下一行
				Queen(n,l+1);
			a[l][j]=0;//回溯回來後或者不可以放置皇后歸0
		}
	}
	return;//如果是if,則遞迴出口,如果是else,則回溯到上一行
}

void Print(int (*a)[8],int n)
{//本演算法打印出N皇后的解
	for(int i=0;i<n;i++)
	{
		for(int j=0;j<n;j++)
		{
			printf("%d ",a[i][j]);
		}
		printf("\n");
	}
}

bool CanPut(int i,int j,int (*a)[8],int n)
{//本演算法是判斷該位置能否放皇后
	int s=0;
	for(int k=i-1;k>=0;k--)
	{
		s++;
		if(a[k][j]==1 || j+s<n&&a[k][j+s]==1 || j-s>=0&&a[k][j-s]==1)
			return false;
	}
	return true;
}