微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

最短树路径顶点

如何解决最短树路径顶点

我们有一个有向图 G(V,E),边上的权重为正,作为源顶点 s 和目标 t。此外,最短的 s - t 路径包括图中的所有其他顶点。 我需要计算 s 和 t 之间的交替最短路径距离,以防某些边 e ∈ E 被删除。我想设计一个 O(E^2 log V) 算法,该算法计算对于所有 e ∈ E,图 G \ e 中最短的 s − t 路径距离。最终输出应该是一个大小为 E 的数组,其中边 e 的条目应该包含 G \ e 中最短的 s − t 路径距离。

解决方法

考虑 S-T 路径(下文中的“主干”)并按路径顺序对 K 个顶点进行编号,其中 S 作为顶点 1。

  • S1 -> V2 -> ... -> VK-1 -> TK子>

将 BBi-j 定义为原始路径的从 i 到 j 的相邻顶点的子路径,包括它们之间的边。

由于 G 中的所有顶点都属于路径,那么 G 中的所有边都在路径中的两个不同顶点之间,命名为 ei->j 从 i 到 j 的有向边。>

从图中移除一条边,唯一相关的情况是边是主干的一部分,在所有其他情况下,路径不会改变。

从主干中移除一条边 ei->j 会破坏它,所以只有在这种情况下我们需要找到一个替代,我们才能证明新的最小最短路径具有以下形式

  • BB1-i' -> ei'->j' -> BBj'-K with i'=j

演示留作练习;-)

替换后的路径长度增加了额外的长度

  • AL(ei->j) = ei->j 的权重 - 子路径 Bi-j
  • 的权重

我们的目标是以最小的额外成本找到一个有效的替换边,这里是伪代码:

Glossary:
- v(i) is the i-th vertex in the backbone
- e(i->j) is the edge going out from v(i) to v(j),in the following we only
  consider edges e(i->j) with j>i,i.e. forward edges,singe backward
  edges can never be part of the solution
- e(*->k),k>j is any edge in the BT terminating in v(k) where k is greater
  than j,the first index is unspecified since edges in BT are only sorted
  by destination vertex
- e(*->q),q<j is any edge in the BT terminating in v(q) where q is lower
  than j,the first index is unspecified since edges in BT are only sorted
  by destination vertex
- BT a binary search tree where we store "best" edges found during the
  iteration,the unique key in BT is the destination vertex's index,so
  we can store here at most one incoming edge per vertex,BT is initially
  empty,during the iteration we buld it so that it has the additional
  property that given two edges e(*->a) e(*->b) in BT,if a<b then also
  AL(e(*->a)) < AL(e(*->b)); in fact BT is ordered at same time both
  by destination index and additional length of the edge
  BT invariants (thanks j_random_hacker): at all times,BT contains only edges that
  1. could be used to form a new path if e(i->i+1) is deleted (because they 
     begin at i or before,and end at i+1 or after)
  2. are not dominated by any other such edge. An edge e(i->j) dominates 
     another edge e(i'->j') if both j >= j' and AL(i->j) < AL(i'->j').
     If edge x dominates edge y,it means that,for each edge-deletion yet
     to be considered (e(i->i+1),e(i+1->i+2),etc.),any replacement path 
     that uses y can always be changed to a shorter path using x,so we don't
     need to care about y

//On each iteration we'll search the solution for removal of edge e(i->i+1)
for each vertex v(i) in S-T in path order,excluding T
  //Discard backward edges,since they can only increase the path length
  for each edge e(i->j) going out from v(i) directed to a vertex v(j) with j>i excluding the backbone edge
    calculate additional length AL(e(i->j))
    search BT using j as key,looking for an egde e(*->k) with k >= j
    if such an edge exists and AL(e(*->k)) <= AL(e(i->j))
      discard the current edge (BT's second property requires that)
    else
      //The current edge is the best choice to reach v(j)
      insert edge in BT (if k==j) discard e(*->k)
      //Now me must check if the new edge can also replace previous
      //ones in the BT to keep the second property valiud,for this we have 
      //to scan the BT in descending order and discard edges with AL >= than
      //the current one
      loop over edges e(*->q) in BT with q<j in descending order
        if AL(e(*->q))>=AL(e(i->j))
          discard e(*->q)
        else
          stop loop
      endloop
    end if
  end for each edge
  //Prune tree from useless edges
  remove from BT all edges with j < i+1
  if BT is empty
    no solution
  else
    select the first edge(i'->j') in BT ==> this is the replacement edge with minimum additional cost,so distance is dist(S-T) + AL(e(i'->j'))
end for each vertex

复杂性:

  • 前两个循环遍历所有边,即 O(|E|)
  • al 的计算是 O(1)
  • 在 BT 中搜索,因为 |BT|
  • 从 BT 中删除边,每条边只能从树中插入和删除一次,因此,对于所有迭代,总共为 O(|E| log |V|)

总共有 O(|E| log |V|)

注意这个问题不需要生成路径,只需要计算距离,如果必须生成路径那么复杂度会增加,因为我们最多可以有|E|长度为 |V| 的路径,然后是 O(|E| |V|)

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。