Ejemplo n.º 1
0
func addMinPathLeft(graph *m.Graph) {
	dp := &m.DijkstraPrio{}
	heap.Init(dp)
	visited := make(map[*m.Node]bool)
	endNode := graph.EndNode()
	endNode.SetMinPathLeft(0)
	visited[endNode] = true
	for _, edge := range endNode.ToEdges() {
		node := edge.From()
		node.SetMinPathLeft(edge.FastestTime())
		heap.Push(dp, node)
	}
	if dp.Len() > 0 {
		for node := heap.Pop(dp).(*m.Node); dp.Len() > 0; node = heap.Pop(dp).(*m.Node) {
			visited[node] = true
			for _, edge := range node.ToEdges() {
				innerNode := edge.From()
				if !visited[innerNode] {
					innerNode.SetMinPathLeft(edge.FastestTime() + node.MinPathLeft())
					heap.Push(dp, innerNode)
				}
			}
		}
	}
}
Ejemplo n.º 2
0
// Route takes a created graph object and finds the shortest path from start to end, returning
// that path as a list of edges.
func Route(graph *m.Graph) []*m.Edge {
	if graph.StartNode() == nil || graph.EndNode() == nil {
		return nil
	}
	addMinPathLeft(graph)
	startPath := m.CreatePath()
	startPath.AddRewards(graph.StartNode().Rewards())
	pq := &m.PrioQueue{}
	heap.Init(pq)
	addNodeEdgesToPrioQueue(pq, graph.StartNode(), startPath)
	for path := prioPath(pq); path != nil; path = prioPath(pq) {
		node := path.Edges()[len(path.Edges())-1].To()
		if node == graph.EndNode() {
			return path.Edges()
		}
		addNodeEdgesToPrioQueue(pq, node, path)
	}
	return nil
}