在这里插入图片描述
在国际象棋中马是走日字的,如果是一般情况马一共有八种走法(如下图):
在这里插入图片描述

 所以我在这边用2个一位数组来表示其8种走法

    //考虑到马有8种走法
    int dx[8]={-2,-1,1,2,-2,-1,2,1};

    int dy[8]={-1,-2,-2,-1,1,2,1,2};

    之后就让马根据这八种走法来走不过还要考虑下面3种情况

    第一种情况

    如果马的下一步走法已经超出棋盘的范围了那么就不应该让马接下来走这一步转而去考虑其他的走法

    第二种情况

     如果马的下一步是已经走过的那么就不应该让马接下来走这一步转而去考虑其他的走法

    第三种情况

    如果马能够遍历完棋盘,那么就要考虑其最后一步是否可以通过上述的八种走法中的一种到达最开始的一步

C++实现:

#include<bits/stdc++.h>
using namespace std;
int N,M;
int a[100][100];
struct Node
{
	int x;
	int y;
};
Node Q[10005];
//定义马走的八个方向
int dir_x[8] = {-1,-2,-2,-1,1,2,2,1}; 
int dir_y[8] = {2,1,-1,-2,-2,-1,1,2};
//打印
void print()
{
	for(int i=0;i<N;i++)
	{
		for(int j=0;j<M;j++)
			printf("(%d,%d) ",Q[i*N+j+1].x,Q[i*N+j+1].y);
		cout<<endl;
	}
	cout<<endl<<endl;
	for(int i=0;i<N;i++)
	{
		for(int j=0;j<M;j++)
		{
			printf("%-3d ",a[i][j]);
		}
		cout<<endl;
	}
}
//判断下一步是否是起始的位置
bool judge(int x,int y)
{
	for(int i=0;i<8;i++)
	{
		if(x+dir_x[i]==0&&y+dir_y[i]==0)//0表示马的起始位置 
			return true;
	}
	return false;
}
void dfs(int cx,int cy,int step)
{
	if(step==N*M+1&&judge(cx,cy))
	{
		print();
		exit(1);
	}
	int tx,ty;
	for(int i=0;i<8;i++)
	{
		tx = cx + dir_x[i];//下一步的坐标x 
		ty = cy + dir_y[i];//下一步的坐标y 
		if(tx<0||tx>=N||ty<0||ty>=M||a[tx][ty]!=0)
		{
			continue;
		}
		Q[step].x=tx;
		Q[step].y=ty;
		a[tx][ty]=step;
		dfs(tx,ty,step+1);
		a[tx][ty]=0;//当遍历完棋盘后将棋盘重新置为0(表示马为走过),起始位置还是1 
	}
}
int main()
{
	cin>>N>>M;
	a[0][0]=1;
	Q[1].x=0;
	Q[2].y=0;
	dfs(0,0,2);
	return 0;
}

运行效果:
在这里插入图片描述

更多推荐