马遍历棋盘高效算法(10*10),10*10以下的棋盘基本可以迅速计算出结果。

//SP3,Intel(R)Pentium(R) processor 1.60GHz,221MHz、768M的内存

 

// 指定任意起始点开始起跳,不重复的踏遍棋盘每一个点。

 

/*

10*10 的棋盘从基本能在半个小时内搜索到路径。

不同的起始点所需的时间不一样。

有的点是无法完成搜索的(不知道是不是算法的原因)。

*/

 

#include <iostream>
#include "time.h"
using namespace std;

 

//定义棋盘的大小
#define BoardSize 10

 

//时间变量,起始、结束时间

clock_t start=0, finish=0;
int iH=0, iL=0;

 

//所跳的步数
int stp = 0;

 

//每一步的坐标,行、列、下一步跳的方向

struct step
{
 int h;     //行
 int l;      //列
 int drt;  //方向
};

step trace[BoardSize*BoardSize]; 

int board[BoardSize][BoardSize];   //画结果用的棋盘

 

//方向

struct direct
{
 int h;
 int l;
};

direct drt[8];

 

void jump();

void main()
{

//任一点所有能跳的方向
 drt[0].h = 1;
 drt[0].l = -2;
 
 drt[1].h = 2;
 drt[1].l = -1;
 
 drt[2].h = 2;
 drt[2].l = 1;
 
 drt[3].h = 1;
 drt[3].l = 2;
 
 drt[4].h = -1;
 drt[4].l = 2;
 
 drt[5].h = -2;
 drt[5].l = 1;
 
 drt[6].h = -2;
 drt[6].l = -1;
 
 drt[7].h = -1;
 drt[7].l = -2;
 
 stp = 0;
 

//输入起始点的坐标,行iH、列iL
 cin>> iH >> iL;
 trace[stp].h = iH;
 trace[stp].l = iL;
 board[iH][iL] = stp+1;

 

start = clock();

 jump();
 finish = clock();

 

 cout<< "所用时长:"<< ((finish - start)/1000)
  <<". "<<((finish - start)%1000)<<"秒"<<endl;
}

 

void jump()
{
 for ( ; ; )
 {
  
  for (int i=trace[stp].drt; i<8; i++)
  {

    //判断当前点的出路
   if (((trace[stp].h + drt[i].h <BoardSize) && (trace[stp].h + drt[i].h >=0))
    && ((trace[stp].l + drt[i].l <BoardSize) && (trace[stp].l + drt[i].l >=0))
    && (board[trace[stp].h+drt[i].h][trace[stp].l+drt[i].l] == 0))
   {
    trace[stp].drt = i;//保存当前点即将要跳的方向

    //下一个点的坐标
    iH = drt[(trace[stp].drt)].h + trace[stp].h;
    iL = drt[(trace[stp].drt)].l + trace[stp].l;


    stp++;
    trace[stp].h = iH;
    trace[stp].l = iL;
    trace[stp].drt = 0;
    board[iH][iL] = stp+1;//标志跳到该点
    i = 0;

    if (stp == (BoardSize*BoardSize-1))//判断是否跳完每一个点
    {
     for (int a=0; a<BoardSize; a++)
     {
      for (int b=0; b<BoardSize; b++)
      {
       if (board[a][b] < 10)
        cout<<0;
       cout <<board[a][b]<<"   ";
      }
      cout <<endl;
      cout <<endl;
     }
     return;
    }
   }
   else
    continue;
  }

//当前点没有出路,则回退到上一点,

//并将当前点标志为未踩过的点
  trace[stp].drt = 0;
  trace[stp].h = 0;
  trace[stp].l = 0;
  stp--;

//如果回退到起始点,

//证明输入的起始点找不到能跳完每一个点的线路,结束
  if (stp <=0)

  {
   cout<< "No Answer" <<endl;
   break;
  }


  board[iH][iL] = 0;
  iH = trace[stp].h;
  iL = trace[stp].l;
  
/

//第二次回跳(很重要,影响算法速度)

//如果某一点的所有方向都不能前进,证明该点的上一点也是无法找到出路的

//这就减少了大量的无用搜索,加快了速度

  trace[stp].drt = 0;
  trace[stp].h = 0;
  trace[stp].l = 0;
  stp--;
  board[iH][iL] = 0;
  iH = trace[stp].h;
  iL = trace[stp].l;


  trace[stp].drt++;//从另一个方向出发

 }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值