0-1 bfs 学习笔记

0-1 bfs 是一种可以在 O(n+m)\mathcal{O}(n + m) 时间求解只含有 0011 两种边权的单源最短路的算法。这种情形下效率比 dijkstra 更高,和 dijkstra 一样好写(甚至更好写一点)。

我们知道边权仅为 11 的最短路(可以看做无权图最短路)可以通过纯 bfs 使用 O(n+m)\mathcal{O}(n + m) 解决,而 dijkstra 是 O((m+n)logn)\mathcal{O}((m+n) \log n) 的,我从这里引入。

dijkstra 之所以有个 logn\log n 就是因为取距离最小的点时存在瓶颈,那么为什么 bfs 只需要取队头呢?因为有了边权仅为 11 的特性,因此无论什么时候,队头到队尾,对应的距离都是单调不降的。

为了方便叙述,我们将 bfs 中队列里的每个元素(代表节点编号)uu 都替换为 dud_u 后的序列记作 qqqq 的开头对应原队列开头。

比如 bfs 中队列 (2,4,3)(2, 4, 3),那么我们的 qq 会表示为 (d2,d4,d3)(d_2, d_4, d_3)。因图而异,这个 qq 可能是 (0,1,1)(0, 1, 1),也有可能是 (2,3,3)(2, 3, 3)……

在无权图最短路中我们每次只会把 qq 的开头 DD pop 掉,然后把若干个(可能没有)D+1D + 1 push 到队列的尾部,那么显然当 qq 初始为 (0)(0) 时,这样操作一定可以恒定使得 qq 单调不降,并且事实上,任何时刻上 qq 一定可以表示成 D,D,,D,D+1,D+1,,D+1D, D, \cdots, D,D+1, D+1, \cdots, D+1 的形式,也就是先一段 DD 后一段 D+1D+1 的形式(可以全都是 DDD+1D +1)。不信你试试看。

但是在 0-1 bfs 中,我们把 DD pop 掉之后,push 进去的点有两种情况:DDD+1D+1。如果我们直接 push 到尾部会破坏单调性。会出现类似于 D,D,D+1,D,D+1D, D, D + 1, D, D + 1 这种支离破碎的情况……怎么办呢?

0-1 bfs 的精髓就来了:

  • 把队头 uu 弹出,遍历 uu 连向的所有节点 vvD=duD = d_u);
  • 尝试松弛 vv,如果成功:
    • 如果 uvu \to v 边权为 11,那么把 vv push 到队尾(把 D+1D + 1 放到 qq 的尾部);
    • 如果 uvu \to v 边权为 00,那么把 vv push 到队头(把 DD 放在 qq 的头部)。

这样处理后 qq 仍然可以时刻表示成 D,D,,D,D+1,D+1,,D+1D, D, \cdots, D,D+1, D+1, \cdots, D+1 的形式。原因也是显然的。

另外,为了保证 dijkstra 每个点只会入队和出队一次,我们需要 vis 数组和松弛操作并用;

而无权最短路 bfs 可以把 vis 数组和松弛操作随便丢一个。

这个想想就知道,无权 bfs 是一层一层往下推,节点 uu 第一次被搜索到的深度就是它的最短路,因此后面再访问 uu 不再需要进行任何操作。

但是 0-1 bfs,我们举个例子,有一张图由以下两部分构成:

  • 1234561 \to 2 \to 3 \to 4 \to 5 \to 6,权值均为 00
  • 161 \to 6,权值为 11

我们会先从 11 拓展到 2266d6d_6 会先被写上 11(假的),后面才能从 55 搜索到 66 从而使 d6=0d_6 = 0,这个修改 d6d_6 的操作需要松弛。所以松弛不能丢

但是 0-1 bfs 直接丢掉 vis 数组是可以的。我们假设当前节点为 uu,正在遍历出边 (u,v,w{0,1})(u, v, w \in \{0, 1\})

  • w=0w = 0 时显然 dv=dud_v = d_u 就是 vv 确定的最短路了
  • w=1w = 1 时,dvd_v 会被标记成 du+1d_u + 1,那么 dvd_v 实际的最短路可能是 du+1d_u + 1 也有可能是 dud_u(显然只有这两种情况),因此 vv 后面可能又会被重新松弛为 dud_u 一次,而且也就最多这一次了

所以一个点最多被入队两次,时间复杂度可以接受。所以不需要 vis 数组~

由于 0-1 bfs 中需要给队列的两端 push,需要使用到双端队列,因此也叫双端队列 bfs 和 dqbfs(?)。

代码就不上了。

posted @   dbxxx  阅读(2827)  评论(3编辑  收藏  举报
相关博文:
阅读排行:
· 单线程的Redis速度为什么快?
· 展开说说关于C#中ORM框架的用法!
· Pantheons:用 TypeScript 打造主流大模型对话的一站式集成库
· SQL Server 2025 AI相关能力初探
· 为什么 退出登录 或 修改密码 无法使 token 失效
历史上的今天:
2020-10-02 放球问题 学习笔记
点击右上角即可分享
微信分享提示