Ho ragione riguardo le differenze tra gli algoritmi di Floyd-Warshall, Dijkstra e Bellman-Ford?

11

Ho studiato i tre e sto affermando le mie inferenze da loro di seguito. Qualcuno potrebbe dirmi se li ho capiti abbastanza bene o no? Grazie.

  1. L'algoritmo di Dijkstra viene utilizzato solo quando si ha una singola fonte e si desidera conoscere il percorso più piccolo da un nodo all'altro, ma fallisce in casi come questo

  2. L'algoritmo di Floyd-Warshall viene utilizzato quando uno qualsiasi di tutti i nodi può essere un'origine, quindi si desidera che la distanza più breve per raggiungere qualsiasi nodo di destinazione da qualsiasi nodo di origine. Questo fallisce solo quando ci sono cicli negativi

(questo è il più importante. Voglio dire, questo è quello di cui sono meno sicuro:)

3.Bellman-Ford è usato come Dijkstra, quando c'è una sola fonte. Questo può gestire pesi negativi e il suo funzionamento è lo stesso di Floyd-Warshall eccetto per una fonte, giusto?

Se hai bisogno di dare un'occhiata, gli algoritmi corrispondenti sono (cortesia Wikipedia):

Bellman-Ford:

 procedure BellmanFord(list vertices, list edges, vertex source)
   // This implementation takes in a graph, represented as lists of vertices
   // and edges, and modifies the vertices so that their distance and
   // predecessor attributes store the shortest paths.

   // Step 1: initialize graph
   for each vertex v in vertices:
       if v is source then v.distance := 0
       else v.distance := infinity
       v.predecessor := null

   // Step 2: relax edges repeatedly
   for i from 1 to size(vertices)-1:
       for each edge uv in edges: // uv is the edge from u to v
           u := uv.source
           v := uv.destination
           if u.distance + uv.weight < v.distance:
               v.distance := u.distance + uv.weight
               v.predecessor := u

   // Step 3: check for negative-weight cycles
   for each edge uv in edges:
       u := uv.source
       v := uv.destination
       if u.distance + uv.weight < v.distance:
           error "Graph contains a negative-weight cycle"

Dijkstra:

 1  function Dijkstra(Graph, source):
 2      for each vertex v in Graph:                                // Initializations
 3          dist[v] := infinity ;                                  // Unknown distance function from 
 4                                                                 // source to v
 5          previous[v] := undefined ;                             // Previous node in optimal path
 6                                                                 // from source
 7      
 8      dist[source] := 0 ;                                        // Distance from source to source
 9      Q := the set of all nodes in Graph ;                       // All nodes in the graph are
10                                                                 // unoptimized - thus are in Q
11      while Q is not empty:                                      // The main loop
12          u := vertex in Q with smallest distance in dist[] ;    // Start node in first case
13          if dist[u] = infinity:
14              break ;                                            // all remaining vertices are
15                                                                 // inaccessible from source
16          
17          remove u from Q ;
18          for each neighbor v of u:                              // where v has not yet been 
19                                                                                 removed from Q.
20              alt := dist[u] + dist_between(u, v) ;
21              if alt < dist[v]:                                  // Relax (u,v,a)
22                  dist[v] := alt ;
23                  previous[v] := u ;
24                  decrease-key v in Q;                           // Reorder v in the Queue
25      return dist;

Floyd-Warshall:

 1 /* Assume a function edgeCost(i,j) which returns the cost of the edge from i to j
 2    (infinity if there is none).
 3    Also assume that n is the number of vertices and edgeCost(i,i) = 0
 4 */
 5
 6 int path[][];
 7 /* A 2-dimensional matrix. At each step in the algorithm, path[i][j] is the shortest path
 8    from i to j using intermediate vertices (1..k−1).  Each path[i][j] is initialized to
 9    edgeCost(i,j).
10 */
11
12 procedure FloydWarshall ()
13    for k := 1 to n
14       for i := 1 to n
15          for j := 1 to n
16             path[i][j] = min ( path[i][j], path[i][k]+path[k][j] );
    
posta Programming Noob 28.07.2012 - 23:05
fonte

1 risposta

3

Se ti capisco correttamente, la tua comprensione è corretta.

  • Djikstra's trova il più piccolo percorso di costo da un nodo sorgente a ogni altro nodo nel grafico, tranne se c'è un fronte di peso negativo. (Dijkstra può essere facilmente trasformato nell'algoritmo A * semplicemente cambiandolo per fermarlo una volta trovato il nodo di destinazione e aggiungendo l'euristica.)
  • Bellman-Ford fa lo stesso di Dijkstra, ma è più lento. Ma può gestire i contorni di peso negativi.
  • Floyd-Warshall trova il costo del più piccolo percorso di costo da ciascun nodo a ogni altro nodo. (Restituisce una matrice numerica). È molto più lento di quello di Djikstra o di Bellman-Ford. A differenza di ciò che hai scritto, non fallisce quando si verifica un ciclo negativo, riporta semplicemente un numero negativo senza significato per il costo di alcuni nodi a se stesso.
risposta data 03.08.2012 - 02:29
fonte

Leggi altre domande sui tag