有障碍的最短路径

时间:2015-03-25 03:40:58

标签: java algorithm graph-algorithm

我们得到N×N雷区(2d阵列),在另一个M×2阵列中给出了地雷的坐标。什么是找到从左上角到右下角的最短路径的最佳算法,而不是踩在雷区的矿井上?

2 个答案:

答案 0 :(得分:2)

这是shortest path problem,可以通过将问题减少到graph来解决:

G=(V,E)
V = { (x,y) | for all x,y such that (x,y) is not a mine } 
E = { ((x1,y1),(x2,y2)) | (x1,y1) is adjacent to (x2,y2) }

现在有了图表,你需要应用一些最短路径算法。

  • 最简单的一个是BFS(因为你的图表没有加权)。这个 实现起来非常简单,并始终找到最快的路径 如此存在。
  • 更复杂的方法是bi-directional BFS。在这里,您从起始节点(0,0)和结束节点(n,n)执行BFS - 并在算法的两个前端相互找到时完成。通过将第一个与第二个相反的方式连接来给出路径。这种方法可能比常规BFS更快,但编程起来有点困难。
  • 您可以使用明智的算法,例如A* search algrotihm,将曼哈顿距离作为启发式函数(假设您只能上/下/右/左,没有对角线)。这可能比两种选择都快,但更难编码。

如果你没有经验,我会从BFS开始,然后转向更高级的alrefithms。

在伪代码中:

BFS(x_source,y_source, x_target,y_target):
   queue = empty new queue
   queue.add(Pair(x_source,y_source))
   parent= new dictionary
   parent.add(source, None)
   while (queue.empty() == false): 
      curr = queue.dequeue()
      currX = curr.first
      currY = curr.second
      if (currX == x_target && currY == y_target)
          return getPath(dict, curr)
      for each neighbor u of curr: //u is a pair of (x,y) coordinates of adjacent cell
          if u is not a key in parent:
             parent[u] = curr
             queue.add(u)

上面的BFS填充parent字典,并且路径由以下getPath()函数返回,该函数基本上遍历字典,直到找到“root”(原始源节点)。 / p>

getPath(dict, target):
   sol = [] //empty list
   curr = target
   while curr != None:
         sol.addFirst(curr)
         curr = dict.get(curr)

答案 1 :(得分:1)

使用dijkstra算法可以解决这个问题。 首先删除所有到Mine节点的传入路径,然后以最短路径前进到右下角节点。