题意:
有一个单身的骑士非常的寂寞,打算去旅行咯,但是强迫症的骑士希望能走过棋盘的任意一格,可以从任意一格开始,判断骑士能不能实现这个愿望,如果可以i请输出路线
思路:
既然要走遍所有格子,那路程一样啦,不需要求最短路什么的,用dfs即可
1、因为所有的格子都要走,我们可以选择一个固定坐标;
2、注意题目要求输出路径字典序最小,所以可以选择(1,1)也就是“A1”作为起点开始搜索;
3、因为要求字典序,所以移动方向一定要注意!纵坐标从左到右,纵坐标一样就横坐标从上到下,这样去规定方向数组dx[]和dy[];
代码:
#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cmath>
#include <queue>
#include <stack>
//从A1这个格子开始搜索,就能保证字典序是小的
//控制移动方向,保证字典序最小
using namespace std;
const int MAXN = 30 + 5;
int n, m;
bool ans;
bool vis[MAXN][MAXN];
int dx[] = {-1,1,-2,2,-2,2,-1,1};
int dy[] = {-2,-2,-1,-1,1,1,2,2};
char recode[(MAXN*MAXN)>>1][2];
void init(){
for(int i=1; i<=n; i++)
for(int j=1; j<=m; j++)
vis[i][j] = false;
vis[1][1] = true;
}
//A1B3C1A2B4C2A3B1C3A4B2C4
void DFS(int x, int y, int step){
int xx, yy;
recode[step][0] = y+'A'-1;
recode[step][1] = x+'0';
if(step == n*m) {ans=true; return;}
for(int i=0; i<8; i++){
xx = x + dx[i];
yy = y + dy[i];
if(xx<1 || xx>n || yy<1 || yy>m || vis[xx][yy] || ans) continue;
vis[xx][yy] = true;
DFS(xx, yy, step+1);
vis[xx][yy] = false;
}
}
int main(){
int t;
int ok = 0;
int no = 0;
scanf("%d", &t);
while(t--){
init();
ans = false;
scanf("%d%d", &n, &m);
DFS(1, 1, 1);
if(ok) puts("");
else ok = 1;
printf("Scenario #%d:\n", ++no);
if(n==1 && m==1) {printf("A1\n"); continue;}
if(ans){
n *= m;
for(int i=1; i<=n; i++) printf("%c%c", recode[i][0], recode[i][1]);
puts("");
}
else printf("impossible\n");
}
return 0;
}
反思:
就是那个字典序磨了很久,额……再仔细一点啦