馬走日
經典回溯題目
給出棋盤和初始座標 問這個馬有多少種方法遍歷整個棋盤
思路
從初始點開始遍歷每一個方向 並查看新點有沒有被遍歷過
如果沒有就走出一步並在這一步繼續搜
搜完需要回溯(恢復搜之前的狀態)
如果搜索的深度達到N*M(即棋盤大小) 則遍歷到了所有點 答案++
直到遍歷完所有方案
代碼
#include<iostream>
#include<cstring>
using namespace std;
int dx[9]={0,1,1,-1,-1,2,2,-2,-2};
int dy[9]={0,2,-2,2,-2,-1,1,1,-1};
int a[111][111];
int t,n,m,x,y,step,sum;
int dfs(int &x,int &y,int step)
{
if(step>=m*n)
{
sum++;
return 0;
}
for(int l=1;l<=8;l++)
{
int x1=x+dx[l];int y1=y+dy[l];
if(x1<n&&y1<m&&x1>=0&&y1>=0&&a[x1][y1]==0)
{
a[x1][y1]=1;
dfs(x1,y1,step+1);
a[x1][y1]=0;
}
}
}
int main()
{
cin>>t;
for(int i=1;i<=t;i++)
{
cin>>n>>m>>x>>y;
a[x][y]=1;
dfs(x,y,1);
cout<<sum<<endl;
memset(a,0,sizeof(a));
sum=0;
}
}
return 0