8皇后问题

来源:互联网 发布:php的底层引擎 编辑:程序博客网 时间:2024/05/29 11:36

8皇后拉斯维加斯算法与回溯法相结合的求解方法

// LasVegasN后问题.cpp : 定义控制台应用程序的入口点。
//
#include "stdafx.h"
#include "targetver.h"
#include <stdio.h>
#include <tchar.h>
#include "stdafx.h"
#include"iostream"
#include<math.h>
#include<time.h>
#include<iomanip>
using namespace std;
const unsigned long maxshort=65535L;
const unsigned long multiplier=1194211693L;
const unsigned long adder=12345L;
class RandomNumber{
private:
 //当前种子
 unsigned long randSeed;
public:
 //构造函数
 RandomNumber(unsigned long s=0);
 unsigned short Random(unsigned long n);
 double fRandom();
};


RandomNumber::RandomNumber(unsigned long s)
{
 if(s==0)
  randSeed=time(0);
 else
  randSeed=s;
}

double RandomNumber::fRandom()
{
 return Random(maxshort)/double(maxshort);
}

unsigned short RandomNumber::Random(unsigned long n)
{
 randSeed=multiplier*randSeed+adder;
 return (unsigned short)((randSeed>>16)%n);
}

class Queen
{
 friend bool nQueen(int);
private:
 //Queen(int m);
 bool Place(int k);//测试皇后k置于第x[k]列的合法性
 bool Backtrack(int t);//解n后问题的回溯法
 bool QueensLV(int stopVegas);//随机放置n个皇后拉斯维加斯算法
 int n,//皇后个数
  *x,*y;
};

 

bool Queen::Place(int k)
{
 //测试皇后k置于第x[k]列的合法性
 for(int j=1;j<k;j++)
  if((abs(k-j)==abs(x[j]-x[k]))||(x[j]==x[k]))
   return false;
 return true;
}


bool Queen::Backtrack(int t)
{
 //解n后问题的回溯法
 if(t>n)
 {
  for(int i=1;i<=n;i++)
   y[i]=x[i];
  return true;
 }
 else
  for(int i=1;i<=n;i++)
  {
   x[t]=i;
   if(Place(t)&&Backtrack(t+1))
    return true;
  }
  return false;
}

 

bool Queen::QueensLV(int stopVegas)
{
 //随机放置n个皇后的拉斯维加斯算法
 RandomNumber rnd;
 int k=1;//下一个放置的皇后编码
 int count=1;
 //1<=stopVegas<=n表示允许随机放置的皇后数
 while((k<=stopVegas)&&(count>0))
 {
  count=0;
  for(int i=1;i<=n;i++)
  {
   x[k]=i;
   if(Place(k))
    y[count++]=i;
  }
  if(count>0)
   x[k++]=y[rnd.Random(count)];//随机位置
 }
 return (count>0);//count>0表示成功
}

bool nQueen(int n)
{
 //解n后问题的拉斯维加斯算法
 Queen X;
 X.n=n;
 int *p=new int[n+1];
 int *q=new int[n+1];
 for(int i=0;i<=n;i++)
 {
  p[i]=0;
  q[i]=0;
 }
 X.x=p;
 X.y=q;
 //设置随机放置皇后的个数
 int stop=8;
 if(n>15)
  stop=n-15;
 bool found=false;
 while(!X.QueensLV(stop));
 
 //算法的回溯搜索部分
 if(X.Backtrack(stop+1))
 {
  for(int i=1;i<=n;i++)
   cout<<p[i]<<" ";
  found=true;
 }
 cout<<endl;
 delete []p;
 delete []q;
 return found;

}

int _tmain(int argc, _TCHAR* argv[])
{
 nQueen(8);
 int x=0;
 cin>>x;
}

 

原创粉丝点击