多源 BFS 算法详解:从原理到实现,高效解决多源最短路问题

news2025/2/23 9:02:33

        多源 BFS 是一种解决 边权为 1 的多源最短路问题 的高效算法。其核心思想是将所有源点视为一个“超级源点”,通过一次 BFS 遍历即可计算所有节点到最近源点的最短距离。以下从原理、实现和代码示例三个方面深入讲解:


目录

一、原理分析

1. 单源 BFS vs 多源 BFS

2. 正确性证明

3. 时间复杂度

二、C++ 实现步骤

1. 初始化

2. BFS 扩展

三、代码示例

四、代码解释

初始化阶段

BFS 扩展阶段

五、应用场景

六、注意事项


一、原理分析

1. 单源 BFS vs 多源 BFS

  • 单源 BFS:从单一源点出发,逐层扩展,记录每个节点到该源点的最短距离。

  • 多源 BFS:将多个源点 同时加入队列,作为 BFS 的初始层。每个节点被首次访问时,记录的是到最近源点的最短距离。

2. 正确性证明

  • BFS 的逐层扩展特性保证:当某个节点被首次访问时,其路径长度即为最短距离。

  • 所有源点同时作为初始层,相当于它们处于“第 0 层”,后续扩展的层数即为到最近源点的距离。

3. 时间复杂度

  • 与单源 BFS 相同,时间复杂度为 O(N)(假设共 N 个节点),每个节点和边仅被处理一次。


二、C++ 实现步骤

以二维网格为例,假设 grid 表示网格,其中 1 为源点,0 为可通行节点。目标是计算每个节点到最近源点的距离。

1. 初始化

  • 队列:将所有源点坐标加入队列。

  • 距离数组:源点距离初始化为 0,其他节点初始化为 -1(表示未访问)。

2. BFS 扩展

  • 从队列中取出节点,检查其四个方向(上、下、左、右)。

  • 若相邻节点未被访问过,更新其距离并加入队列。


三、代码示例

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

vector<vector<int>> multiSourceBFS(vector<vector<int>>& grid) {
    int rows = grid.size();
    int cols = grid[0].size();
    queue<pair<int, int>> q;
    vector<vector<int>> dist(rows, vector<int>(cols, -1));

    // 初始化:将所有源点加入队列,并设置距离为 0
    for (int i = 0; i < rows; i++) {
        for (int j = 0; j < cols; j++) {
            if (grid[i][j] == 1) {
                q.push({i, j});
                dist[i][j] = 0;
            }
        }
    }

    // 四个移动方向:上、下、左、右
    vector<pair<int, int>> dirs = {{-1, 0}, {1, 0}, {0, -1}, {0, 1}};

    while (!q.empty()) {
        auto [x, y] = q.front();
        q.pop();

        for (auto [dx, dy] : dirs) {
            int nx = x + dx;
            int ny = y + dy;

            // 检查边界和是否已访问
            if (nx >= 0 && nx < rows && ny >= 0 && ny < cols && dist[nx][ny] == -1) {
                dist[nx][ny] = dist[x][y] + 1;
                q.push({nx, ny});
            }
        }
    }

    return dist;
}

四、代码解释

  1. 初始化阶段

    • 遍历网格,将所有源点(值为 1)的坐标加入队列,并设置其距离为 0

    • 其他节点的距离初始化为 -1,表示未访问。

  2. BFS 扩展阶段

    • 从队列中取出节点,检查四个方向的相邻节点。

    • 若相邻节点在网格内且未被访问,更新其距离为当前节点距离 +1,并将其加入队列。


五、应用场景

  • 计算多个起点到所有节点的最短距离(如疫情传播模拟、火源蔓延模型)。

  • 地图中多个商店到用户的最短路径计算。


六、注意事项

  1. 边权必须为 1:若边权不同,需使用 Dijkstra 或 Floyd-Warshall 算法。

  2. 空间优化:可直接在原数组上修改距离,避免额外空间开销。

  3. 性能优势:相比暴力法(每个源点单独 BFS),时间复杂度从 O(kN) 优化到 O(N),其中 k 是源点数量。

        通过多源 BFS,我们能够以高效的方式解决多个起点同时扩散的最短路径问题,是图论中一种重要的优化技巧。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2303841.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Jenkins 构建 Unity 打包 .apk 同时生成 .aab

Jenkins 构建 Unity 打包 .apk 同时生成 .aab Android App Bundle简称 AAB&#xff0c;想了解更多关于 AAB 的知识&#xff0c;请看官网 https://developer.android.google.cn/guide/app-bundle/faq?hlzh-cn APK 打包部分在复用上一篇 Jenkins 构建 Unity打包APK 一、新建一…

清华大学第五弹:《DeepSeek与AI幻觉》

作者&#xff1a;清华大学新闻与传播学院新媒体研究中心、人工智能学院&#xff08;新媒沈阳团队&#xff09; 时间&#xff1a;2025年2月 完整版下载地址&#xff1a;夸克网盘分享 一、AI幻觉的定义与分类 定义 学术定义&#xff1a;模型生成与事实不符、逻辑断裂或脱离上下…

分布式数据库解析

title: 分布式数据库解析 date: 2025/2/20 updated: 2025/2/20 author: cmdragon excerpt: 通过金融交易、社交平台、物联网等9大真实场景,结合Google Spanner跨洲事务、DynamoDB毫秒级扩展等38个生产级案例,揭示分布式数据库的核心原理与工程实践。内容涵盖CAP定理的动态…

Zotero 快速参考文献导出(特定期刊引用)

目录 一、添加样式 每次投期刊时每种期刊的引用方式不一样&#xff0c;就很麻烦。发现zeotero添加期刊模板再导入很方便 一、添加样式 然后就能导出自己想要的期刊格式的引用了

库的制作与原理(一)

1.库的概念 库是写好的&#xff0c;现成的可以复用的代码。本质上库是一种可执行的二进制形式&#xff0c;可以被操作系统载入内存执行。库有俩种&#xff1a;静态库 .a[Linux] .lib[windows] 动态库 .so[Linux] .dll[windows] 就是把.c文件变成.o文件&#xff0c;把…

go 日志框架

内置log import ("log""os" )func main() {// 设置loglog.SetFlags(log.Llongfile | log.Lmicroseconds | log.Ldate)// 自定义日志前缀log.SetPrefix("[pprof]")log.Println("main ..")// 如果用format就用PrintF&#xff0c;而不是…

Rust配置笔记

1.Node.js下载配置 2.c环境配置 C我是用vs装的点击这个installer 点击修改 选择C环境就行,这个时候它就帮忙配置环境了 3.Rust下载配置 4.装napi-rs框架 npm install -g napi-rs/cliRust下载网站 下完之后直接打开 一开始下包会比较慢,多等等 下好之后跑项目前第一件事配置…

具有整合各亚专科医学领域知识能力的AI智能体开发纲要(2025版)

整合各亚专科医学领域知识能力的AI代理的开发与研究 一、引言 1.1 研究背景 在科技飞速发展的当下,人工智能(AI)已成为推动各行业变革的关键力量,医疗领域也不例外。近年来,AI 在医疗行业的应用取得了显著进展,从医学影像诊断到疾病预测,从药物研发到个性化医疗,AI 技…

数据表的存储过程和函数介绍

文章目录 一、概述二、创建存储过程三、在创建过程中使用变量四、光标的使用五、流程控制的使用六、查看和删除存储过程 一、概述 存储过程和函数是在数据库中定义的一些SQL语句的集合&#xff0c;然后直接调用这些存储过程和函数来执行已经定义好的SQL语句。存储过程和函数可…

为AI聊天工具添加一个知识系统 之117 详细设计之58 思维导图及观察者效应 之2 概念全景图

&#xff08;说明&#xff1a;本文和上一篇问题基本相同&#xff0c;但换了一个模型 deepseek-r1&#xff09; Q1227、在提出项目“为使用AI聊天工具的聊天者加挂一个专属的知识系统”后&#xff0c;我们已经进行了了大量的讨论-持续了近三个月了。这些讨论整体淋漓尽致体现了…

Error [ERR_REQUIRE_ESM]: require() of ES Module

报错信息&#xff1a; 【报错】Message.js 导入方式不对&#xff0c;用的是 ES Moudle 的语法&#xff0c;提示使用 import 引入文件 项目开发没有用到 js-message 依赖&#xff0c;是 node-ipc 依赖中用到的 js-message 依赖&#xff0c; node-ipc 中限制 js-message 版本&a…

GStreamer源码安装1.24版本

从官网下载 1.24的源码包 https://gitlab.freedesktop.org/gstreamer/gstreamer/-/tree/1.24?ref_typeheads#getting-started &#xff0c;尝试过使用git clone 的方式&#xff0c;但速度贼慢&#xff0c;就选择了下载源码包的方式安装依赖 sudo apt install libssl-dev g me…

从CNN到Transformer:遥感影像目标检测的未来趋势

文章目录 前言专题一、深度卷积网络知识专题二、PyTorch应用与实践&#xff08;遥感图像场景分类&#xff09;专题三、卷积神经网络实践与遥感影像目标检测专题四、卷积神经网络的遥感影像目标检测任务案例【FasterRCNN】专题五、Transformer与遥感影像目标检测专题六、Transfo…

从 x86 到 ARM64:CPU 架构的进化与未来

在计算机发展的历史长河中&#xff0c;x86、x64 和 ARM64 这三大主流 CPU 架构各自书写了辉煌的篇章。它们不仅代表了技术的进步&#xff0c;更承载着无数创新者的梦想与努力。 x86&#xff1a;从 16 位到 32 位的辉煌之路 诞生与崛起 1978 年&#xff0c;英特尔&#xff08;…

Java数据结构第十二期:走进二叉树的奇妙世界(一)

专栏&#xff1a;数据结构(Java版) 个人主页&#xff1a;手握风云 目录 一、树型结构 1.1. 树的定义 1.2. 树的基本概念 1.3. 树的表示形式 二、二叉树 2.1. 概念 2.2. 两种特殊的二叉树 2.3. 二叉树的性质 2.4. 二叉树的存储 三、二叉树的基本操作 一、树型结构 1.…

【AI时代】基于AnythingLLM+ Ollama + DeepSeek 搭建本地知识库

一、本地安装Ollama及DeepSeek 参考教程&#xff1a; https://blog.csdn.net/Bjxhub/article/details/145536134 二、下载并安装AnythingLLM AnythingLLM下载地址&#xff1a; https://anythingllm.com/ 傻瓜式安装即可 可以自定义安装路径。三、配置AnythingLLM并使用 3.…

leetcode刷题记录(一百一十五)——64. 最小路径和

&#xff08;一&#xff09;问题描述 64. 最小路径和 - 力扣&#xff08;LeetCode&#xff09;64. 最小路径和 - 给定一个包含非负整数的 m x n 网格 grid &#xff0c;请找出一条从左上角到右下角的路径&#xff0c;使得路径上的数字总和为最小。说明&#xff1a;每次只能向下…

UE5 编辑器辅助/加强 插件搜集

1. Actor Locker 地址&#xff1a;https://www.fab.com/listings/ec26ac5e-4720-467c-a3a6-b5103b6b74d0 使用说明&#xff1a;https://github.com/Gradess2019/ActorLocker 支持&#xff1a;5.0 – 5.5 简单的编辑器扩展。它允许你通过世界轮廓窗口/热键/上下文菜单在编辑器视…

怎么在Github上readme文件里面怎么插入图片?

环境&#xff1a; Github 问题描述&#xff1a; 怎么在Github上readme文件里面怎么插入图片&#xff1f; https://github.com/latiaoge/AI-Sphere-Butler/tree/master 解决方案&#xff1a; 1.相对路径引用 上传图片到仓库 将图片文件&#xff08;如 .png/.jpg&#xff…

什么是矩阵账号?如何高效运营tiktok矩阵账号

‍‌​​‌‌​‌​‍‌​​​‌‌​​‍‌​​​‌​‌​‍‌​​‌​​‌​‍‌​‌‌​‌‌‌‍‌​‌​‌​​​‍‌​​‌​‌‌​‍‌​​​​‌‌​‍‌​‌​​‌‌‌‍‌​​‌‌​‌​‍‌​‌​​‌‌‌‍‌​‌‌‌​​‌‍‌‌​​‌‌‌​‍‌‌​​‌‌​​‍‌…