题目来源于《算法导论》第15章动态规划的习题 15-1,显然建议使用DP
对最小距离大家应该都比较熟悉,比如对非负权值图中有Dijkstra算法,对负权值图中有Ford算法。 最远距离?假设从A到F的最远距离为A->C->D->E->F, 为什么D->E->F一定会是从D到F的最远距离?我在这点证明困扰了很久,直到最近才想明白其中原理。
当重新审视有向(directed) 无回路(acyclic)这两个词时,我才突然想到原来可以这样证明:
依然假设A到F的最远距离为A->C->D->E->F, 现在考虑从D到F:如果存在B,使得D->B->F更远,那么我们直接可以用这段路径代替D->E->F, 这与我们之前的假设相矛盾;如果D经过C再到达F的距离更远,比如D->C->(E)->F, 那就说明存在回路D<->C, 这与条件相矛盾。所以,这里,D->E->F必然是从D到F的最远路径。算法的理论基础终于找到了!
OK,既然最远子路径是问题的必要条件,那么反过来,我们找到每一个点(除了终点以外)到达终点的最远路径,就可以作为整个问题的充分条件。我们需要一个合适的顺序,遍历所有顶点,从终点开始,逐渐向外扩展。问题到了这里就很明显了,采用拓扑序,广度优先的方式遍历。
具体实现中,我用了一个queue存放BFS中覆盖到的顶点。注意在每加入一个新的顶点v时,除了要遍历已计算过的顶点再确定最大的path[v]时,还要反过来考虑对于已经计算过最远距离的顶点u,如果存在权边u->v,那么path[u]也可能需要更新,这一步是最远路径问题相比于最短路经多出来的一步。
建议同学们自己实现一遍整个方法。因为对于图论问题,实现算法会产生很多自己独到的感觉,尤其是一些辅助性的数据结构。以下是我的一份实现:
int longestpath(int** adjMtx, int n, int s, int t){
int*
动态规划求解有向无回路图最远距离

本文介绍了如何利用动态规划解决有向无回路图中两点间的最远距离问题。通过证明最远子路径的必要性和充分条件,提出采用拓扑序和广度优先搜索的方法,并提供了算法实现的思考与示例。
最低0.47元/天 解锁文章
2003

被折叠的 条评论
为什么被折叠?



