百度:
分析:
其实也是一种贪心算法,从第一行的第一列开始,找满足条件的组合,比如:先把第一行第一列的储存到数组,然后在第二行找满足条件的皇后,找到去第三行,没有找到,回到第一行,找第二列,重复,有就继续找,没有就回到后面一点。
dfs最重要的就是回退和前进,回退是指走通了或者走到低换个方向。前进是按照方向前进,可以选择。
代码:
#include <iostream>
#include <stdio.h>
#include <cstring>
#include <string>
#include <vector>
#include <map>
#include <algorithm>
#include <set>
#include <cmath>
#include <math.h>
#include <iomanip>
#include <array>
using namespace std;
vector<int> v;
int sum=0;
int ok(int i,int j)//判断选取的点是否满足要求
{
for(int i1=0;i1<v.size();++i1)
{
if(abs(i1-i)==abs(v[i1]-j)||v[i1]==j)
{
return -1;
}
}
return 1;
}
void print(int n)//输出找到的皇后解决方案
{
int **a;
a=new int*[n];
for(int i=0;i<n;++i)
{
a[i]=new int[8];
for(int j=0;j<n;++j)
a[i][j]=0;
}
for(int i=0;i<v.size();++i)
{
a[i][v[i]]=1;
}
for(int i=0;i<n;++i)
{
for(int j=0;j<n;++j)
{
cout<<a[i][j]<<" ";
}
cout<<endl;
}
cout<<endl;
}
void dfs(int n)
{
int t=0,i=0;
v.push_back(0);//开始探索
while(1)
{
int j=t;
for(;j<n;++j)
{
if(ok(v.size(),j)==1)//从行中找到满足的列
{
v.push_back(j);
t=0;
break;
}
}
//print();
if(v.size()==0)//当数组个数为0时,则结束了探索
{
return;
}
if(v.size()==n)//等于n时则说明找到了 ,输出,换个方向前进
{
print(n);
sum++;
t=v[v.size()-1]+1;
v.pop_back();
}
if(j==n)//代表这一行没有满足的,换方向,就是回退
{
t=v[v.size()-1]+1;
v.pop_back();
}
if(j>n||v.size()>n)//代表要回退二步,
{
v.pop_back();
t=v[v.size()-1]+1;
v.pop_back();
}
//print();
}
}
int main()
{ int n=0;
cin>>n;
dfs(n);cout<<sum;
return 0;
}