ACWing.1116 马走日(DFS)题解

ACWing.1116 马走日(DFS)题解

题目描述

马在中国象棋以日字形规则移动。

请编写一段程序,给定 n∗m 大小的棋盘,以及马的初始位置 (x,y),要求不能重复经过棋盘上的同一个点,计算马可以有多少途径遍历棋盘上的所有点。

输入格式

第一行为整数 T,表示测试数据组数。

每一组测试数据包含一行,为四个整数,分别为棋盘的大小以及初始位置坐标 n,m,x,y。

输出格式

每组测试数据包含一行,为一个整数,表示马能遍历棋盘的途径总数,若无法遍历棋盘上的所有点则输出 0。

数据范围

1≤T≤9,
1≤m,n≤9,
0≤x≤n−1,
0≤y≤m−1

输入样例:

1
5 4 0 0

输出样例:

32

题解(DFS)

​ 分析:马只能走“日”字形,那么移动一次只能有八种情况出现,如图所示。

在这里插入图片描述

​ 很显然,是DFS模型的变形,把可以到达的邻接点距离写成数组,再分析题目,由于要寻找多条道路,故每次寻路完毕需要进行回溯。贴上代码。

#include <iostream>
#define xa x + a[i]
#define yb y + b[i]
using namespace std;

int m, n, x, y, cnt = 0;
const int a[]={1,2,2,1,-1,-2,-2,-1};
const int b[]={2,1,-1,-2,-2,-1,1,2};
bool g[10][10];

void dfs(int x, int y, int dc){
    if(dc == 0){
        cnt ++;
        return;
    }
    g[x][y] = true;
    for(int i = 0; i < 8; i++){
        if(xa >= 0 && xa < m && yb >= 0 && yb < n && !g[xa][yb]) 
            dfs(xa, yb, dc - 1);
    }
    g[x][y] = false;
}

int main(){
    int t = 0; 
    cin >> t;
    while(t--){
        cin >> m >> n >> x >> y;
        dfs(x, y, n * m - 1);
        cout << cnt << endl;
        cnt = 0;
    }
    return 0;
}

猜你喜欢

转载自blog.csdn.net/yanweiqi1754989931/article/details/109247649