我可以使用什么算法来查找图中指定节点类型之间的最短路径?
这就是问题:
我有 n 个点(p1、p2、p3、.. pn),每个点都可以以确定的成本 x 连接到任何其他点。
每个点都属于一组点类型中的一个(例如“A”“B”“C”“D”...)。
该方法的输入是我想要遵循的路径,例如“ABCADB”。
输出是连接我在输入中给出的类型的点的最短路径,例如“p1-p4-p32-p83-p43-p12”,其中p1是A型,p4是B型,p32是C型型,p83 为 A 型,p43 为 D 型,p12 为 B 型。
“简单”的解决方案包括计算所有可能的路径,但计算成本非常高!
有人能找到更好的算法吗?
正如我在标题中所说,我不知道它是否存在!
更新:
阻止我使用 Dijkstra 和其他类似算法的关键点是我必须根据类型链接点。
作为输入,我有一个类型数组,我必须按该顺序链接。
这是肯特·弗雷德里克(Kent Fredric)的图像(非常感谢),它描述了初始情况(红色允许链接)!
一个现实生活中的例子:
一个人想早上参观教堂,去餐馆,最后下午参观博物馆。
地图上有 6 座教堂、30 家餐厅和 4 家博物馆。
他希望教堂-休息区-博物馆的距离尽可能小。
This is the problem:
I have n points (p1, p2, p3, .. pn), each of them can connect to any other with a determined cost x.
Each point belongs to one of a set of point-types (for example "A" "B" "C" "D"...).
The input of the method is the path I want to follow, for example "A-B-C-A-D-B".
The output is the shortest path connecting the points of the type I give in input so for example "p1-p4-p32-p83-p43-p12" where p1 is an A-type, p4 a B-type, p32 a C-type, p83 an A-type, p43 a D-type and p12 a B-type.
The "easy" solution consists of calculating ALL the possible paths but the computational cost is very high!
Can someone find a better algorithm?
As I said in title, I don't know if it exists!
Update:
The key point that prevents me from using Dijkstra and the other similar algorithms is that I have to link the points according to type.
As input I have an array of types and I have to link in that order.
This is an image of Kent Fredric (thanks a lot) which describes the initial situation (in red allowed links)!
A real life example:
A man wants to visit a church in the morning, go to restaurant and finally visit a museum in the afternoon.
In the map there are 6 churchs, 30 restaurants and 4 museums.
He wants that the distance church-rest-museum is the minimum possible.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(8)
有许多算法比计算所有可能的路径做得更好。 广度优先搜索是我想到的算法系列的基本起点, 最佳优先搜索 是合适的,因为您已经定义了顶点成本,并且如果可以的话要获取有关您的问题空间的更多信息,您可以使用 A* 或 Dijkstra 算法。 (在每种情况下,从允许的起始节点集中查找路径。)
重新编辑:您的路径约束(需要满足的节点类型数组)不会阻止您使用这些算法;您可以使用这些算法。 恰恰相反,它可以帮助他们更好地工作。 您只需要以允许合并路径约束的方式实现它们,将搜索中每个步骤可用的顶点限制为给定约束的有效顶点。
There are many algorithms that will do better than calculating all the possible paths. Breadth-first search is the basic starting point for the family of algorithms I have in mind, Best-first search is appropriate because you have vertex costs defined, and if you can get more information about your problem space, you may be able to use A* or Dijkstra's algorithm. (In each case, finding the paths from the set of allowed starting nodes.)
Re your edit: Your path constraint (the array of node types you need to satisfy) doesn't prevent you from working with these algorithms; quite the opposite, it helps them all work better. You just need to implement them in a way that allows the path constraint to be incorporated, limiting the vertices available at each step in the search to those that are valid given the constraint.
这就是我目前解释您的问题的方式。
红色箭头是我手动跟踪符合给定排序约束的路径。
未提供成本,但假设所有链路都会产生成本,并且链路成本不同。
如果这准确地描述了您要解决的场景,请这么说,以便其他人可以更好地回答问题。
This is how I presently interpret your problem.
Red arrows are me manually tracing the paths that conform to the given ordering constraint.
Costs are not provided, but it is assumed all links incur a cost, and the link costs are different.
If this accurately describes the scenario you are trying to solve, please say so, so that others can better answer the question.
在修改您的问题时,您似乎要求每个字母一个节点 - 在这种情况下,这是一个简单的动态编程解决方案:计算每对节点之间满足序列开头的所有长度为 1 的最短路径。 然后,对于所有节点对来说,拥有 k 个所有此类路径,那么构造 k+1 就很简单了。
On the revision of your question it seems you ask for one node per letter - in that case it is a simple dynamic programming solution: Calculate all the shortest paths of length 1, which satisfy the beginning of your sequence, between each pair of nodes. Then having for k all such paths for all node pairs, it is trivial to construct for k+1.
这是动态编程解决方案的伪代码:
您的最小成本路径是 min(d[n][0..m])
您可以将 d 表的大小减少到 2 行,但这会混淆解决方案
Here is pseudocode with dynamic programming solution:
your minimum cost path is min(d[n][0..m])
you can reduce size of d table to 2 rows, but it would obfuscate the solution
据我了解你的问题,你需要有向图中的最短路径。 http://en.wikipedia.org/wiki/Dijkstra%27s_algorithm 应该给你一个主意。
问候,简
As far as I understand your question you need a shortest path in a directed graph. http://en.wikipedia.org/wiki/Dijkstra%27s_algorithm should give you an idea.
regards, Jan
希望这一点是清楚的。
这个解决方案不是特别有效,但显然是多项式的。
Hope this is clear.
This solution is not particularly efficient, but clearly polynomial.
您可以使用 Floyd–Warshall 算法。 这是维基百科给出的伪代码:
我必须为关于同一问题的算法课程编写一个程序。 这个算法很有魅力! 祝你好运。
You can use the Floyd–Warshall algorithm. Here's the pseudocode given by WikiPedia:
I had to write a program for an algorithms course about this same problem. This algorithm worked like a charm! Goodluck.
正如 Jan 提到的,你只需要一个普通的无聊最短路径算法(比如 Dijkstra 的或 Floyd 的算法); 但是,您需要转换输入图,以便输出路径遵循您的路径约束。
给定路径约束:A - B - A
创建一个新图
G
并使用新标签将A
中的所有顶点插入到G
中像a_01。 然后将B
中的所有顶点插入到G
中,并将A
顶点与B
顶点连接起来(边应该是指向新插入的节点)从原始图中复制成本。 然后,您可以使用A
(以及任何其他路径组件)重复此步骤,将新插入的顶点连接到B
中的顶点。 因此,您创建一个图形,其中只有存在的路径满足路径约束。 然后您可以使用普通的最短路径算法。关键的见解是,当您重新访问一个类时,您实际上正在访问一组不同的节点,并且您只需要连接相邻节点类的边。
As Jan mentioned, you just need a normal boring shortest path algorithm (like Dijkstra's or Floyd's algorithm); however, you need to transform your input graph so that the output path will respect your path constraint.
Given a path constraint of: A - B - A
Create a new graph
G
and insert all of the vertexes fromA
intoG
with new labels like a_01. Then insert all the vertexes fromB
intoG
and connect theA
vertexes with theB
vertexes (edges should be directed towards the newly inserted nodes) copying the costs from the original graph. You then repeat this step withA
(and any other path components) connecting the newly inserted vertexes to those inB
. Thus, you create a graph where only the paths that exist satisfy the path constraint. You can then use normal shortest path algorithms.The key insight is that when you revisit a class you are actually visiting a distinct set of nodes and that you only want edges that connect adjacent classes of nodes.