Using Dijkstra to detect multiple shortest paths

本秂侑毒 提交于 2019-12-24 00:36:48

问题


Given a weighted directed graph, how can the Dijkstra algorithm be modified to test for the presence of multiple lowest-cost paths between a given pair of nodes?

My current algorithm is as follows: (credit to Weiss)

/**
 * Single-source weighted shortest-path algorithm. (Dijkstra) 
 * using priority queues based on the binary heap
 */
public void dijkstra( String startName )
{
    PriorityQueue<Path> pq = new PriorityQueue<Path>( );

    Vertex start = vertexMap.get( startName );
    if( start == null )
        throw new NoSuchElementException( "Start vertex not found" );

    clearAll( );
    pq.add( new Path( start, 0 ) ); start.dist = 0;

    int nodesSeen = 0;
    while( !pq.isEmpty( ) && nodesSeen < vertexMap.size( ) )
    {
        Path vrec = pq.remove( );
        Vertex v = vrec.dest;
        if( v.scratch != 0 )  // already processed v
            continue;

        v.scratch = 1;
        nodesSeen++;

        for( Edge e : v.adj )
        {
            Vertex w = e.dest;
            double cvw = e.cost;

            if( cvw < 0 )
                throw new GraphException( "Graph has negative edges" );

            if( w.dist > v.dist + cvw )
            {
                w.dist = v.dist +cvw;
                w.prev = v;
                pq.add( new Path( w, w.dist ) );
            }
        }
    }
}

回答1:


Replace field prev, the link to previous vertex with a collection prevs, and change the code slightly:

...

        if( w.dist >= v.dist + cvw ) {
            if ( w.dist > v.dist + cvw ) {
                w.dist = v.dist +cvw;
                w.prevs.clear();
            }
            w.prevs.add(v);
            pq.add( new Path( w, w.dist ) );
        }

...



回答2:


If you only want to find a single other equal-cost path

Let's suppose you already ran Dijkstra's algorithm once to get a shortest path P. You can add a tiny cost epsilon to each edge in P and run Dijkstra's a second time on the modified graph to get a new path P'. If P and P' contain the same edges, then you can conclude that P is the unique shortest path. Otherwise, we undo the epsilon change and compare the lengths of P and P'. If the lengths are equal, then clearly P' is another distinct shortest path. Otherwise, P is the unique shortest path.

If we want to find all shortest paths

Such an algorithm would necessarily be exponential-time. This is because a graph can have exponentially-many equal-cost paths between two nodes. For example, consider the graph:

A --> B1 --> C --> D1 --> E ...
  \       ->   \       ->
   -> B2 /      -> D2 /

There are 4 paths from A to E, and if we assume that all edges are equal cost, then all of those paths have equal total cost. By repeating this pattern we can get exponentially-many paths of equal cost.



来源:https://stackoverflow.com/questions/50411987/using-dijkstra-to-detect-multiple-shortest-paths

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!