在jgrapht

时间:2016-11-24 15:59:58

标签: jgrapht

jgrapht支持在两个节点之间的边/顶点上放置一个wehight(成本)的想法。这可以使用DefaultWeightedEdge类来实现。

在我的图表中,我确实要求找不到最短的路径但是最便宜的路径。最便宜的路径可能更长/有更多的跳跃节点然后行进最短的路径。 因此,可以使用DijkstraShortestPath算法来实现这一目标。

但是,我的用例有点复杂:它还需要评估到达节点时需要执行的操作的成本。

让我们说,你有一个像棋盘一样的图形(8x8字段,每个字段都是一个节点)。所有边缘的重量均为1.要在汽车中从左下角移动到对角线(右上角),有许多路径,成本为16.您可以采用zic zac风格的对角线路径,或者您可以先将所有节点向右移动,然后向上移动所有节点。 不同之处在于:当采用zic zac时,您需要沿着移动方向旋转自己。你旋转了16次。 首先向右移动然后向上移动时,您只需要旋转一次(可能是两次,具体取决于您的开始方向)。 因此,从Djikstra的角度来看,zic zac路径是完美的。从逻辑的角度来看,这是最糟糕的。

长话短说:如何在节点或边缘上花费一些成本,具体取决于该路径中的前一个边/节点?我没有在jgrapht的源代码中找到任何相关内容。 或者有更好的算法可供使用吗?

1 个答案:

答案 0 :(得分:1)

这不是JGraphT问题,而是图算法问题。您需要考虑如何编码此问题并更详细地将其形式化

  1. 在顶点上加上权重通常很容易。假设每个顶点代表访问一个客户,这需要a_i时间。这可以通过在节点i中的每个输入弧的成本中加上a_i / 2来编码,并在每个输出弧的成本中加上a_i / 2.

  2. 一种成本函数,其中从j到k依赖于你曾经前往j的弧(i,j)的成本更加复杂。

  3. 方法a:使用动态编程(标记)算法。这可能是最简单的。您可以将成本函数定义为递归函数,其中遍历弧的成本取决于先前弧的成本。

    方法b。:通过一些技巧,您可以通过向其添加额外节点来对图表中的成本进行编码。这是一个例子:

    给出具有顶点{a,b,c,d,e}的图,其中弧为:(a,e),(e,b),(c,e),(e,d)。该图表示顶点e位于中间的十字路口。从a-> e-> b(直线)是自由的,然而,从a-> e-> d转向需要额外的时间。类似于c-> e-> d(直)是自由的并且c-> e-> b(转向)应该受到惩罚。 在4个新顶点中对顶点e去耦:e1,e2,e3,e4。 添加以下弧: (a,e1),(e3,b),(c,e2),(e4,d),(e2,e3),(e1,e3),(e1,e4),(e2,e4)。 (e1,e4)和(e2,e3)可以具有正的权重来惩罚转弯。