旅程规划师,图表数据和Java

时间:2011-01-04 20:58:53

标签: java algorithm oop shortest-path

我正在为我的一些工作寻求一些帮助。

任务是创建伦敦地铁旅程计划。

修改: -

目前,我在HashTable中有一个边缘数据节点的邻接列表。

我想找到一种方法来使用广度优先搜索来获得任意两个顶点之间的最短路径。

顶点在管图看起来逻辑上连接。每个站的边缘通过使用:(this_station,next_station,tube_line)< - 这是关于每个站的信息。

遍历这个非常棘手。任何帮助都非常感谢!

4 个答案:

答案 0 :(得分:3)

这是一个经典的图论问题。您可以将停靠点表示为节点,将停靠点之间的连接表示为边缘。

要直接回答您的问题,我认为将线段表示为单行的最佳方法是制作代表所有线的图形。您可以使用数据标志(或标志集)标记边缘,以表示节点所属的行。最终,无论线路,站点和分段如何,这都是图表。如果您有兴趣表示这些概念,我建议存储它们的方式将是节点(或边)的属性。

如果您对移除这些边缘感兴趣,可以迭代地去除纯粹中间的边缘。因此,如果A-> B-> C,并且B没有其他连接,则可以移除B并将其B-> C权重添加到A-> C权重。

使用图表表示可以将现有的最短路径算法应用于您的问题。

祝你好运!

-Brian J. Stinar -

答案 1 :(得分:3)

作为Brian implies,你需要一个加权图 - 每条边上的重量应该是火车在两端车站之间行驶的时间。然而,这还不够:您还需要考虑列车在平台上停留的停留时间,在车站不同线路上的平台之间行走所花费的时间,以及您在等待列车时等待火车的时间平台。

令人高兴的是,您可以在加权有向图的框架内完成此操作。您只需将每个工作站表示为一个小子图。要使用整个网络中心和宇宙中心的芬斯伯里公园,作为一个例子,你将有节点:

  1. 车站的入口(有三个,但你可以选择一个)
  2. 一名站在维多利亚南行平台上的乘客
  3. 火车抵达维多利亚南行线平台
  4. 火车从维多利亚南行线平台出发
  5. 其他三个平台的节点2-4的等价物
  6. 然后你们之间有边缘:

    1. 从入口到站在每个平台上,加权作为在它们之间行走的时间
    2. 从每个平台回到入口,以相同的方式加权(这可能是同一时间,所以你可以使这个边缘双向)
    3. 从火车到达平台,重量为零(因为没时间下车)
    4. 在每对平台之间,重量等于在它们之间行走所花费的时间
    5. 从平台到火车出发,重量等于连续列车间隔的一半(因为如果你在一个随机时间到达一个平台,那就是你需要等火车的平均时间)< / LI>
    6. 从火车到达同一平台上的火车出发,重量等于停留时间(只要小于半间隔,否则每次更换火车似乎更快站!)
    7. 然后,您将每个出发节点连接到下一站的到达节点。

      要规划从A到B的路线,您会在站点入口的节点之间找到路径。该路线不仅包括在火车上花费的时间,还包括它们之间的变化。对于许多车站,您可以将许多停留时间和交换时间视为零,但对于某些车站而言,它们非常重要:例如,在绿色公园的维多利亚和皮卡迪利线之间切换,或者在Aldgate的圆线上停留时间。您应该考虑到这些,或者您将制定错误的短途旅行计划。你肯定也需要考虑频率 - 它在一个计划之间产生了显着的差异,比如,Circle线,你可以期待花费三分半钟等待火车出现,以及中央线,它只有一个。

      这种方法仍然没有考虑的一点是频率在分支之间分裂的方式。例如,您可以模拟在Tufnell公园的北行列车的等待时间为1.5分钟,但如果您要前往Mill Hill East,您可能需要等待更长时间,因为大部分列车将通往Barnet。你可能需要在Finchley Central - Mill Hill East边缘增加一些时间来解释这个问题,但我不确定它的适用性如何。

      至于搜索算法,Dijkstra的算法会做,但A*将是经典选项。

答案 2 :(得分:2)

一种选择是将问题表示为图形问题,并对最短路径应用成本优化来解决问题的旅程规划方面。一个常见的选择是应用Dijkstra。引用维基百科的定义:

  

对于给定的源顶点(节点)   图表,算法找到   成本最低的路径(即   这个顶点和。之间的最短路径)   每隔一个顶点。它也可以   用于寻找最短的成本   从单个顶点到单个顶点的路径   通过停止目标顶点   算法一旦到达最短路径   目的地顶点已经   确定。

对于Java,您可以在herehere

中找到一些有趣的注释

Dijkstra的改进算法是A *,其表现更好。这里有一个实现它的project

答案 3 :(得分:1)

这真是一个单独的问题,所以我会尝试给你一个单独的答案。

我认为你选择哈希的内部表示可能会搞砸你。你应该仍然可以使用哈希来处理工作,但是如果你看一下Wikipedia上的伪代码,你会注意到队列被用于邻接列表。我也尝试将邻接列表视为此应用程序的队列。这使得获得每个节点的邻接列表变得非常简单,这是您希望在广度优先搜索下操作的。然后,如果你想把它改成一个堆栈,你就可以超级轻松地获得深度优先搜索。在我看来,你已经读过这个算法,并且你有一般的软件开发能力。在我看来,如果我在你的情况下会让我感到沮丧,但这可能是任何事情。

祝你好运!

-Brian J. Stinar -