当前位置:首页 > 洛谷 > 洛谷P1443题解:BFS算法求解马的移动问题

洛谷P1443题解:BFS算法求解马的移动问题

1个月前 (08-09)

洛谷P1443题解:BFS算法求解马的移动问题 洛谷题解 广度优先搜索 广搜 BFS算法 队列 第1张

一、题目解读

洛谷P1443题要求计算在n×m的棋盘上,马从起点(x, y)出发,到达每个位置所需的最少移动步数。题目中“马”遵循国际象棋的移动规则(即走“日”字),需输出整个棋盘各点到起点的最短步数矩阵。该问题本质是求解多源最短路径,但考虑到马的移动特性,采用广度优先搜索BFS算法能高效解决。

二、解题思路

核心思路为:

1. BFS算法:利用队列存储待遍历的位置,从起点开始逐层扩散,确保首次到达某点的步数即为最短。

2. 方向数组优化:预先定义马可移动的8个方向(dx, dy),避免每次计算偏移量,提升效率。

3. 标记已访问:使用board数组记录步数,初始值-1表示未访问,避免重复计算。

4. 边界检查:在扩展新位置时,需判断是否在棋盘内且未被访问,保证算法正确性。

三、解题步骤

1. 初始化:读取棋盘尺寸n×m和起点坐标(x, y),创建board数组并初始化为-1,队列q存入起点。

2. BFS主循环:

    弹出队首位置,获取其坐标和步数。

    遍历8个方向,计算新坐标(nx, ny)。

    若新位置合法且未访问,更新board[nx][ny]为当前步数+1,并加入队列。

3. 输出结果:遍历board数组,按格式输出每个位置的步数。

四、代码与注释

#include <iostream>
#include <queue>
#include <vector>
#include <cstring>
using namespace std;

// 定义马移动的8个方向
const int dx[8] = {1, 2, 2, 1, -1, -2, -2, -1};
const int dy[8] = {2, 1, -1, -2, -2, -1, 1, 2};

int main() {
    int n, m, x, y;
    cin >> n >> m >> x >> y;
    
    // 初始化棋盘,所有位置设为-1
    vector<vector<int>> board(n+1, vector<int>(m+1, -1));
    queue<pair<int, int>> q;
    
    // 起点设置为0步
    board[x][y] = 0;
    q.push({x, y});
    
    while (!q.empty()) {
        auto current = q.front();
        q.pop();
        int cx = current.first;
        int cy = current.second;
        
        // 尝试8个方向
        for (int i = 0; i < 8; i++) {
            int nx = cx + dx[i];
            int ny = cy + dy[i];
            
            // 检查新位置是否在棋盘内且未被访问
            if (nx >= 1 && nx <= n && ny >= 1 && ny <= m && board[nx][ny] == -1) {
                board[nx][ny] = board[cx][cy] + 1;
                q.push({nx, ny});
            }
        }
    }
    
    // 输出结果
    for (int i = 1; i <= n; i++) {
        for (int j = 1; j <= m; j++) {
            cout << board[i][j] << " ";
        }
        cout << endl;
    }
    
    return 0;
}

注释说明:

● dx/dy数组:硬编码马的8个移动方向,减少重复计算。

● board初始化为-1:标记未访问状态,避免误判。

● BFS循环:通过队列逐层扩展,确保最短性。

● 边界检查:确保新位置合法,防止越界。

五、总结

本解法通过BFS算法,结合方向数组优化,实现了对马移动最短路径的高效求解。时间复杂度为O(nm),空间复杂度为O(nm),适用于大多数棋盘规模。该思路同样适用于其他类似“多源最短路径”问题,体现了BFS在形遍历中的通用性。掌握此类算法对提升算法设计与优化能力具有重要意义。


原创内容 转载请注明出处

分享给朋友:

相关文章

洛谷1363题解法:虚拟坐标优化BFS解决循环迷宫问题(附代码详解)

洛谷1363题解法:虚拟坐标优化BFS解决循环迷宫问题(附代码详解)

一、题目解读洛谷1363题要求判断在给定大小的循环迷宫中,从起点出发是否可以通过移动到达多个不同的路径方向。迷宫由字符矩阵表示,'S'为起点,'#'为障碍物,其余为可通...

洛谷P2190题解:铁路售票系统车厢计算(差分数组+前缀和优化)

洛谷P2190题解:铁路售票系统车厢计算(差分数组+前缀和优化)

一、题目解读洛谷P2190题要求解决铁路售票系统中的车厢数量计算问题。题目给定n个车站和m条订票申请,每条申请包含区间[x,y)及乘客数z。需要计算在不超载的情况下(每节车厢最多36人),满足所有乘客...

洛谷P1141题解:迷宫连通块问题的深度优先搜索算法与代码解析

洛谷P1141题解:迷宫连通块问题的深度优先搜索算法与代码解析

一、题目解读洛谷P1141题目要求处理一个由字符构成的迷宫,其中相同字符形成连通块,不同字符构成分隔。题目需统计连通块数量及大小,并支持查询两点是否属于同一连通块。核心在于高效识别并标记迷宫中的连通区...

洛谷P3393题解:基于多源BFS与Dijkstra算法求解图论最小花费路径问题

洛谷P3393题解:基于多源BFS与Dijkstra算法求解图论最小花费路径问题

一、题目解读洛谷P3393题要求在一个包含N个城市和M条双向道路的图中,求解从起点1到终点N的最小花费路径。图中存在僵尸城市(僵尸无法通过)和危险城市(由僵尸城市扩散S步后标记),需要避开所有危险城市...

洛谷P2789题解:递归算法与避免重复计算的技巧

洛谷P2789题解:递归算法与避免重复计算的技巧

一、题目解读洛谷P2789题要求计算n条直线在平面上两两相交产生的交点总数。题目强调交点不重复,需考虑平行线情况。关键点在于如何高效枚举所有可能的交点组合,并排除重复结果。二、解题思路采用递归算法,核...

洛谷P1438题解:基于线段树的等差数列

洛谷P1438题解:基于线段树的等差数列

一、题目解读洛谷P1438题要求处理数列的区间更新与单点查询操作,其中更新方式为给定区间内元素按等差数列递增。传统暴力修改会因多次区间遍历导致超时,需设计高效数据结构——线段树,结合等差数列性质实现O...

发表评论

访客

看不清,换一张

◎欢迎参与讨论,请在这里发表您的看法和观点。