【问题标题】:Finding length of shortest cycle in undirected graph在无向图中找到最短循环的长度
【发布时间】:2014-01-17 19:21:09
【问题描述】:

我尝试了以下方法:

1) DFS,跟踪我的 DFS 树中每个顶点的级别

2) 每次看到一个后边(x,y),我计算循环长度=level[x] - level[y] + 1,如果小于最短则保存

有人可以举一个反例说明这种方法是错误的吗?

在无向图中找到最短循环的更好方法是什么?

谢谢。

【问题讨论】:

  • 这个过程应该可以正常工作。顺便说一句,如果图的节点太少,你也可以用 Floyd-Warshall 算法找到最小的循环(实现传递闭包矩阵)但是 Floyd Warshall 算法需要 O(V^3) 计算时间,而 DFS 只需要 O( V+E)
  • @Fallen 我认为这也可以,直到我在 Dasgupta 发现一个问题,询问为什么相同的方法是错误的并要求提供反例;所以这绝对不应该是正确的。这是我找到的问题的链接(请看最后的练习 4.4):cs.berkeley.edu/~vazirani/algorithms/chap4.pdf
  • 我错过了 DFS 树,抱歉。恕我直言,BFS 树应该可以正常工作。在 DFS 方式中,可以在较短的路径之前访问较长的路径。

标签: algorithm data-structures graph


【解决方案1】:

为什么 DFS 不起作用

您不能使用 DFS 来找到最短的圆。我们可以轻松地创建一个反例,其中 DFS 线索仅找到最长的圆。让我们看看下面的图表:

如您所见,我们有九个节点。如果我们从最左边的节点 A 开始,可能会出现以下 DFS 级别:

我们在迭代时有两个后边:

  • (B , A),因此我们找到了一个长度为 8 的圆
  • (D , A),因此我们找到了一个长度为 8 的圆

但是,最短的圆的长度为 5。它在下一张图片中显示为蓝色,而之前找到的一个圆显示为红色:

您没有看到蓝色圆圈,因为您的 DFS 路径不包含它。 Dagupa 等人也在他们的书中提到了这种行为:

但这也意味着 DFS 最终可能会采用一条漫长而复杂的路线到达实际上非常接近的顶点。

为什么 BFS 不起作用

嗯,这并不完全正确,可以使用 BFS(参见下一小节),但不能使用公式。拿下图:

这张图还没有花哨的图片。 每个“o”都是一个节点。 o---o | | +-------o---o--------+ | | o----o----o----o----o

让我们看看 BFS 中可能有哪些级别。如果我从中间的节点开始,我会得到以下级别:

5~~~5 ~~~ 是后边 | | +-------4~~~4--------+ | | 3----2----1----2----3

如果我从左侧节点开始,我会得到以下级别:

3~~~4 | | +-------2---3--------+ | | 1----2----3----4~~~~4

因此,您不能使用等级公式。

解决方案

虽然效率不高,但使用全对最短路径算法并检查每个节点的距离 (i,i) 是一种有效的解决方案。

【讨论】:

  • +1,很好的例子。我只是在“修复 BFS”部分中更改 back edge 术语,它们不应该存在于 BFS 遍历中。
  • @Leeor:在 BFS 中调用的冲突/不一致边是什么?他们有什么特别的名字吗?
  • 我认为它们将是交叉边缘,后边缘连接到祖先,这在 BFS 中是不可能的。我也觉得你的复杂性太悲观了。
  • @tor 让我们举个例子。为了简单起见,假设深度(p(c))>深度(a)。如果我们引入 a--c 和 b--p(c),如果从根开始,我们将有以下检查顺序:p(ab);a,b;c,p(c);其中a,b分别。 c,p(c) 将在同一迭代中检查。一旦你从 p(c) 开始,你就会遇到到 c 的后边(交叉边?已经有一段时间了)。您从 p(c) 和 c 开始到该路径上的共同祖先,即 p(ab)。因此,你找到了 p(ab)-a-c-p(c)-b-p(ab)。
  • @tor 自我编写该算法以来已经快四年了,所以我不得不查看我实际在做什么,但是是的,你是对的。我删除了那个算法。顺便说一下,还有一个更简单的反例。取一个由具有奇数个节点的线组成的图。设端点分别称为A和B。引入X和Z,连接A-X-B和A-Z-B。最短的循环是 A-X-B-Z-A,但算法本可以返回 A-…-B-X/Z-A。与上面的反例基本相同。不过,全对最短路径仍然有效。
【解决方案2】:

我想这就是你要找的东西:https://web.archive.org/web/20170829175217/http://webcourse.cs.technion.ac.il/234247/Winter2003-2004/ho/WCFiles/Girth.pdf

您从每个节点创建一个 BFS,因此您的复杂度为 O(V*E)

【讨论】:

  • 谢谢,链接已修复!我链接的 pdf 在无向图上使用 BFS :)
  • 谢谢!我在考虑另一个问题:找到一个包含特定顶点 v 的最短循环。
  • 我能想到 O(E * deg(v))。
【解决方案3】:

假设我们有以下边的图,

14, 42, 43, 23, 31

然后循环 1、4、2、3、1 可以在 1、4、3、1 之前遍历,并且由于我们正在考虑 DFS,因此不会访问任何节点两次。因此,如果首先遍历 1、4、2、3、1,则根本不可能遍历 1、4、3、1 或 4、2、3、3。因此,使用 DFS,可以确保我们将始终获得最短的周期。

可能的改进: BFS 树应该可以逐级运行,并且对于 BFS 树来说,从根到任何节点的距离是固定的,无论节点被选中的顺序是什么。运行时间:O(V+E),而修改后的 Floyd-Warshall 算法在最坏情况下运行时间为 O(V^3)。

【讨论】:

  • 这张图怎么样? pastebin.com/rT7Y1AUN 如果从 1 开始,我认为 O(V+E) 算法没有帮助。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-08-17
  • 2019-02-15
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多