它有些微妙,但是下面的伪代码可以做到。
首先从v
进行广度优先搜索,以查找每个城市到目标的距离。这为我们提供了distance_remaining
查找,其中distance_remaining[city]
是最短路径(不考虑加油站)。
要实施,我们首先需要一个Visit
数据结构,其中包含有关旅行中访问城市的信息。我们需要哪些字段?
city
fillups
range
last_visit
接下来,我们需要一个优先级队列(就像Dijkstraa一样),以考虑可能的访问。此队列应按我们可能会采取的最短总体行程来优先安排访问。就是说visit.fillups * max_range + (max_range - visit.range) + distance_remaining[visit.city]
。
最后,我们需要一个visited[city]
数据结构来说明是否访问过一个城市。在Dijkstra中,我们仅考虑尚未访问的节点。我们需要进行调整,以仅在尚未访问节点或访问范围小于我们当前节点的访问范围时考虑节点(即使空节点出现故障,一辆满载的汽车也可能会完成)。
现在我们实现以下逻辑:
make visit {city: u,fillups: 0,range: max_range,last_visit: None}
add to priority queue the visit we just created
while v = queue.pop():
if v.city == u:
return v.fillups # We could actually find the path at this point!
else if v not in visited or visited[v.city] < v.range:
for each road r from v.city:
if r.length < v.range:
add to queue {city: r.other_city,fillups: v.fillups,range:v.range - r.length,last_visit: v}
if v.city has fillup station:
add to queue {city: v.city,fillups: fillups + 1,last_visit: v}
return -1
本文链接:https://www.f2er.com/3102384.html