You are on page 1of 22

Grafo de Floyd-Warshall

Lógica Matemática

Juan Esteban Morales Gómez

Juan David Londoño Ladino

Universidad Libre de Pereira

Sede Belmonte

Risaralda - Pereira

2018
Grafo de Floyd-Warshall

Lógica Matemática

Juan Esteban Morales Gómez

Juan David Londoño Ladino

Docente: Carlos Alberto Ocampo Sepulveda

Universidad Libre de Pereira

Sede Belmonte

Risaralda - Pereira

2018
Tabla de contenido

Introducción..................................................................................................................................... 4
Algoritmo de Floyd-Warshall ...................................................................................................... 5
Características ............................................................................................................................ 5
Función ......................................................................................................................................... 6
Aplicaciones ................................................................................................................................ 7
El Algoritmo de Warshall.............................................................................................................. 8
El Algoritmo de Floyd.................................................................................................................... 8
Robert W. Floyd: ......................................................................................................................... 9
Pseudocódigo del algoritmo Floyd-Warshall ................................................................... 14
Código C++ del algoritmo Floyd-Warshall......................................................................... 15
Ejemplo ................................................................................................................................... 16
Bibliografía ..................................................................................................................................... 22
Introducción
Las técnicas heurísticas para recorrido de grafos han sido utilizadas en muchas
aplicaciones como la solución de circuitos eléctricos, en la exploración de entornos
en robótica móvil, en el control de información en redes Informáticas, entre otras.
Esto se debe a que todos los sistemas mencionados pueden ser modelados como
grafos. Esto también es aplicable en el caso de las redes de distribución, donde
cada nodo en la red de distribución es un nodo del grafo, y cada línea entre los
nodos de la red de distribución, es un arco en el grafo. Para este caso se
consideraron redes radiales, que son las más comunes en las redes de distribución,
por lo que en los grafos no se obtenían trayectorias cerradas.
Algoritmo de Floyd-Warshall

El problema que intenta resolver este algoritmo es el de encontrar el camino más


corto entre todos los pares de nodos o vértices de un grafo. Esto es semejante a
construir una tabla con todas las distancias mínimas entre pares de ciudades de un
mapa, indicando además la ruta a seguir para ir de la primera ciudad a la segunda.
Este es uno de los problemas más interesantes que se pueden resolver con
algoritmos de grafos.

Existen varias soluciones a este problema y los algoritmos a aplicar dependen


también de la existencia de arcos con pesos o costes negativos en el grafo. En el
caso de no existir pesos negativos, sería posible ejecutar V veces el algoritmo de
Dijkstra para el cálculo del camino mínimo, donde V es el número de vértices o
nodos del grafo. Esto conllevaría un tiempo de ejecución de O (V^3) (aunque se
puede reducir). Si existen arcos con pesos negativos, se puede ejecutar también V
veces el Algoritmo de Bellman-Ford, una vez para cada nodo del grafo. Para grafos
densos (con muchas conexiones o arcos) esto conllevaría un tiempo de ejecución
de O (V^4).

El algoritmo de Floyd-Warshall (‘All-Pairs-Shortest-Path’ – Todos los caminos


mínimos) ideado por Floyd en 1962 basándose en un teorema de Warshall también
de 1962, usa la metodología de Programación Dinámica para resolver el problema.
Éste puede resolver el problema con pesos negativos y tiempos de ejecución
iguales a O (V^33); sin embargo, para ciclos de peso negativo el algoritmo tiene
problemas. A continuación, se muestra el pseudocódigo del algoritmo.

Características
Obtiene la mejor ruta entre todo par de nodos.

Trabaja con la matriz D inicializada con las distancias directas entre todo par de
nodos.

La iteración se produce sobre nodos intermedios, o sea para todo elemento de la


matriz se prueba si lo mejor para ir de i a j es a través de un nodo intermedio elegido
o como estaba anteriormente, y esto se prueba con todos los nodos de la red. Una
vez probados todos los nodos de la red como nodos intermedios, la matriz resultante
da la mejor distancia entre todo par de nodos.

El algoritmo da sólo la menor distancia; se debe manejar información adicional para


encontrar tablas de encaminamiento.

Hasta no hallar la última matriz no se encuentran las distancias mínimas.

Su complejidad es del orden de N3.

Función
Compara todos los posibles caminos a través del grafo entre cada par de vértices.
El algoritmo es capaz de hacer esto con sólo V3 comparaciones, lo hace mejorando
una estimación del camino más corto entre dos vértices, hasta que se sabe que la
estimación es óptima.

Sea un grafo G con conjunto de vértices V, numerados de 1 a N. Sea además una


función caminoMinimo(i,j,k) que devuelve el camino mínimo de i a j usando
únicamente los vértices de 1 a k como puntos intermedios en el camino. Ahora, dada
esta función, el objetivo es encontrar el camino mínimo desde cada i a cada j usando
únicamente los vértices de 1 hasta k + 1.

Hay dos candidatos para este camino: un camino mínimo, que utiliza únicamente
los vértices del conjunto (1...k); o bien existe un camino que va desde i hasta k + 1,
después de k + 1 hasta j que es mejor. Sabemos que el camino óptimo de i a j que
únicamente utiliza los vértices de 1 hasta k está definido por caminoMinimo(i, j,k), y
está claro que si hubiera un camino mejor de i a k + 1 a j, la longitud de este camino
sería la concatenación del camino mínimo de i a k + 1 (utilizando vértices de (1...k))
y el camino mínimo de k + 1 a j (que también utiliza los vértices en (1...k)).

Por lo tanto, podemos definir caminoMinimo(i,j,k) de forma recursiva:


CaminoMinimo(i,j,k) = min(CaminoMinimo(i,j,k-1),CaminoMinimo(i,k,k-
1)+CaminoMinimo(k,j,k-1)); CaminoMinimo(i,j,0) = pesoArista(i,j);
Esta fórmula es la base del algoritmo Floyd-Warshall. Funciona ejecutando primero
CaminoMinimo(i,j,1) para todos los pares (i,j), usándolos para después hallar
CaminoMinimo(i,j,2) para todos los pares (i,j)... Este proceso continúa hasta que k
= n, y habremos encontrado el camino más corto para todos los pares de vértices
(i,j) usando algún vértice intermedio.

Para que haya coherencia numérica, Floyd-Warshall supone que no hay ciclos
negativos (de hecho, entre cualquier pareja de vértices que forme parte de un ciclo
negativo, el camino mínimo no está bien definido porque el camino puede ser
infinitamente pequeño). No obstante, si hay ciclos negativos, Floyd-Warshall puede
ser usado para detectarlos. Si ejecutamos el algoritmo una vez más, algunos
caminos pueden decrementarse, pero no garantiza que, entre todos los vértices,
caminos entre los cuales puedan ser infinitamente pequeños, el camino se reduzca.
Si los números de la diagonal de la matriz de caminos son negativos, es condición
necesaria y suficiente para que este vértice pertenezca a un ciclo negativo

Aplicaciones
El algoritmo de Floyd-Warshall puede ser utilizado para resolver los siguientes
problemas:

Camino mínimo en grafos dirigidos (algoritmo de Floyd).

Cierre transitivo en grafos dirigidos (algoritmo de Warshall). Es la formulación


original del algoritmo de Warshall. El grafo es un grafo no ponderado y representado
por una matriz booleana de adyacencia. Entonces la operación de adición es
reemplazada por la conjunción lógica(AND) y la operación menor por la disyunción
lógica (OR).

Encontrar una expresión regular dada por un lenguaje regular aceptado por un
autómata finito (algoritmo de Kleene).

Inversión de matrices de números reales (algoritmo de Gauss-Jordan).

Ruta óptima. En esta aplicación es interesante encontrar el camino del flujo máximo
entre 2 vértices. Esto significa que en lugar de tomar los mínimos con el
pseudocódigo anterior, se coge el máximo. Los pesos de las aristas representan las
limitaciones del flujo. Los pesos de los caminos representan cuellos de botella; por
ello, la operación de adición anterior es reemplazada por la operación mínimo.

Comprobar si un grafo no dirigido es bipartito.

El Algoritmo de Warshall
El algoritmo de Warshall es un ejemplo de algoritmo booleano. A partir de una tabla
inicial compuesta de 0`s (no hay correspondencia inicial en el grafo) y 1`s (hay una
correspondencia, llamase “flecha”, entre nodos), obtiene una nueva matriz
denominada “Matriz de Clausura Transitiva” en la que se muestran todas las
posibles uniones entre nodos, directa o indirectamente. Es decir, si de “A” a “B” no
hay una “flecha”, es posible que si haya de “A” a “C” y luego de “C” a “B”. Luego,
este resultado se verá volcado en la matriz final.

El Algoritmo de Floyd
El algoritmo de Floyd es muy similar, pero trabaja con grafos ponderados. Es decir,
el valor de la “flecha” que representamos en la matriz puede ser cualquier entero o
infinito. Infinito marca que no existe unión entre los nodos. Esta vez, el resultado
será una matriz donde estarán representadas las distancias mínimas entre nodos,
seleccionando los caminos más convenientes según su ponderación (“peso”). Por
ejemplo, si de “A” a “B” hay 36 (km), pero de “A” a “C” hay 2(km) y de “C” a “B” hay
10 (km), el algoritmo nos devolverá finalmente que de “A” a “B” hay 12 (km).

Los pasos a dar en la aplicación del algoritmo de Floyd son los siguientes:

* Formar las matrices iniciales C y D.

* Se toma k=1.

* Se selecciona la fila y la columna k de la matriz C y entonces, para i y j, con i≠k,


j≠k e i≠j, hacemos:Si (Cik + Ckj) < Cij → Dij = Dkj y Cij = Cik + Ckj
En caso contrario, dejamos las matrices como están.

* Si k ≤ n, aumentamos k en una unidad y repetimos el paso anterior, en caso


contrario páramos las interacciones.

* La matriz final C contiene los costes óptimos para ir de un vértice a otro, mientras
que la matriz D contiene los penúltimos vértices de los caminos óptimos que unen
dos vértices, lo cual permite reconstruir cualquier camino óptimo para ir de un vértice
a otro.

Robert W. Floyd:
Nació el 8 de junio de 1936 en Nueva York, es profesor de la Stanford University
(B.A. Chicago 1955 B.S. Chicago 1958), y en 1978 fue galardonado con el
prestigioso premio A.M. Turing que otorga la ACM para reconocer las contribuciones
de naturaleza técnica realizadas a la comunidad informática. El premio le fue
concedido por tener una influencia clara en las metodologías para la creación de
software eficiente y fiable, y por ayudar a fundar las siguientes áreas de la
informática: teoría de análisis sintáctico, semántica de los lenguajes de
programación, verificación automática de programas, síntesis automática de
programas y análisis de algoritmos.

Fue uno de los inventores del deterministic linear time selection algorithm. También
introdujo mejoras en los algoritmos quicksort y quickselect.

Paso a paso

Se deriva de varios pasos de los cuales se explicaran mediante el siguiente ejemplo:


Ejemplo: encontrar el camino mas corto entre los siguientes pares de nodos del
siguiente grafo:
Primer paso:
Hallamos la matriz de distancia del grafo:
d 1 2 3 4
1 0 5 ∞ ∞
i 50 0 15 5
2
3 30 ∞ 0 15
4 15 ∞ 5 0

Segundo paso:
Inicializamos la matriz de predecesores
p 1 2 3 4
1 X X X X
2 X X X X
3 X X X X
4 X X X X
j

Tercer paso
Se elaboran nuevas tablas de distancia y predecesores de esta manera
d 0 1 2 3
0 0 5 ∞ ∞
i 50 0 15 5
1
2 30 ∞ 0 15
3 15 ∞ 5 0

p 0 1 2 3
0 X X X X
1 X X X X
2 X X X X
3 X X X X
j

La idea es realizar iteraciones para cambiar el valor de los ∞ decir que para este
grafo se deben realizar 4 iteraciones.
Cuarto paso: k=0; i=2; j=1;
Primera Iteración: k=0; i=2; j=1;
D (2,1) < D (2,0) + D (0,1)?→ ∞<30+5? →D(2,1)= 35
d 0 1 2 3
0 0 5 ∞ ∞
50 0 15 5
1
2 30 35 0 15
3 15 ∞ 5 0
p 0 1 2 3
0 X X X X
1 X X X X
2 X 0 X X
3 X X X X
Quinto paso: k=0; i=3; j=1
D (3,1) < D (3,0) + D (0,1)? =>∞<15+5? => D(3,1)= 20
d 0 1 2 3 p 0 1 2 3
0 0 5 ∞ ∞ 0 X X X X
50 0 15 5 1 X X X X
1 2 X 0 X X
2 30 35 0 15 3 X 0 X X
3 15 20 5 0

Sexto paso: k=1; i=0; j=2


D(0,2) < D (0,1)+ D(1,2) => ∞< 5+15? => D (0,2) = 20
d 0 1 2 3 p 0 1 2 3
0 0 5 20 ∞ 0 X X 1 X
50 0 15 5 1 X X X X
1 2 X 0 X X
2 30 35 0 15 3 X 0 X X
3 15 20 5 0

Séptimo paso: k=1; i=0; j=3


D(0,3) < D(0,1) + D(1,3) => ∞< 5+5 => D(0,3)=10

d 0 1 2 3 p 0 1 2 3
0 0 5 20 10 0 X X 1 1
50 0 15 5 1 X X X X
1 2 X 0 X X
2 30 35 0 15 3 X 0 X X
3 15 20 5 0

Octava paso: k=2; i=1; j=0


D (1,0) < D (1,2) + D (2,0) => 50<15+30 D (1,0) = 45
d 0 1 2 3 p 0 1 2 3
0 0 5 20 10 0 X X 1 1
45 0 15 5 1 2 X X X
1 2 X 0 X X
2 30 35 0 15 3 X 0 X X
3 15 20 5 0

Noveno paso: k=3; i=0; j=2


D(0,2)<D(0,3)+D(3,2) => 20<10+5 D(0,2)=15
d 0 1 2 3 p 0 1 2 3
0 0 5 15 10 0 X X 3 1
45 0 15 5 1 2 X X X
1 2 X 0 X X
2 30 35 0 15 3 X 0 X X
3 15 20 5 0

Decimo paso: k=3; i=1; j=0


D(1,0)<D(1,3)+D(3,0)? => 45<5+15? D(1,0)= 20
d 0 1 2 3 p 0 1 2 3
0 0 5 15 10 0 X X 3 1
20 0 15 5 1 3 X X X
1 2 X 0 X X
2 30 35 0 15 3 X 0 X X
3 15 20 5 0

Decimo primer paso: k=3; i=1; j=2


D(1,2)<D(1,3)+D(3,2)? =>15 <5+5? D(1,2)=10
d 0 1 2 3 p 0 1 2 3
0 0 5 15 10 0 X X 3 1
20 0 10 5 1 3 X 3 X
1 2 X 0 X X
2 30 35 0 15 3 X 0 X X
3 15 20 5 0

Decimo segundo paso:


Las Matrices Resultantes que contiene la distancia mínimas y la ruta a seguir entre
un par de nodos son:

d 1 2 3 4 p 1 2 3 4
1 0 5 15 10 1 -1 -1 4 2
20 0 10 5 2 4 -1 4 -1
2 3 -1 1 -1 -1
3 30 35 0 15 4 -1 1 -1 -1
4 15 20 5 0

En el cuadro de los predecesores indica que la ruta mínima es 1, 2, 4

Pseudocódigo del algoritmo Floyd-Warshall


1/* La función pesoArista devuelve el coste del camino que va de i a j

2(infinito si no existe).

3 y n es el número de vértices y pesoArista(i,i) = 0


4 */

5 int camino[ ][ ];

6 /* Una matriz bidimensional. En cada paso del algoritmo, camino[i][j] es el


camino mínimo

7 de i hasta j usando valores intermedios de (1..k-1). Cada camino[i][j] es


inicializado a

8 pesoArista(i,j)

9 */

10 procedimiento FloydWarshall ()

11 para k: = 0 hasta n − 1

12 para todo (i,j) en (0..n − 1)

13 camino[i][j] = mín ( camino[i][j], camino[i][k]+camino[k][j]);

Código C++ del algoritmo Floyd-Warshall


// Declaraciones en el archivo .h

int cn; //cantidad de nodos

vector< vector<int> > ady; // [[matriz de adyacencia]]

// Devuelve una matriz con las distancias mínimas de cada nodo al resto de los
vértices.

vector< vector<int> > Grafo :: floyd(){

vector< vector<int> > path = this->ady;

for(int i = 0; i < cn; i++)

path[i][i] = 0;

for(int k = 0; k < cn; k++)


for(int i = 0; i < cn; i++)

for(int j = 0; j < cn; j++){

int dt = path[i][k] + path[k][j];

if(path[i][j] > dt)

path[i][j] = dt;

return path;

Ejemplo

Hallar el camino mínimo desde el vértice 3 hasta 4 en el grafo con la siguiente


matriz de distancias:

Aplicamos el algoritmo de Floyd-Warshall, y para ello en cada iteración fijamos un


vértice intermedio.

1ª Iteración: nodo intermedio = 1

La matriz es simétrica, por lo que solamente hará falta calcular el triángulo


superior de las distancias.

d23 = min(d23, d21 + d13) = 8

d24 = min(d24, d21 + d14) = 4

d25 = min(d25, d21 + d15) = 9


d26 = min(d26, d21 + d16) =

d32 = min(d32, d31 + d12) = 8

d34 = min(d34, d31 + d14) = 6

d35 = min(d35, d31 + d15) = 7

d36 = min(d36, d31 + d16) = 1

d45 = min(d45, d41 + d15) =

d46 = min(d46, d41 + d16) = 4

d56 = min(d56, d51 + d16) =

La matriz de distancia después de esta iteración es:

2ª Iteración: nodo intermedio = 2

d13 = min(d13, d12 + d23) = 5

d14 = min(d14, d12 + d24) = 1

d15 = min(d15, d12 + d25) = 12

d16 = min(d16, d12 + d26) =

d34 = min(d34, d32 + d24) = 6

d35 = min(d35, d32 + d25) = 7

d36 = min(d36, d32 + d26) = 1

d45 = min(d45, d42 + d25) = 13


d46 = min(d46, d42 + d26) = 4

d56 = min(d56, d52 + d26) =

La matriz de distancia después de esta iteración es:

3ª Iteración: nodo intermedio = 3

d12 = min(d12, d13 + d32) = 3

d14 = min(d14, d13 + d34) = 1

d15 = min(d15, d13 + d35) = 12

d16 = min(d16, d13 + d36) = 6

d24 = min(d24, d23 + d34) = 4

d25 = min(d25, d23 + d35) = 9

d26 = min(d26, d23 + d36) = 9

d45 = min(d45, d43 + d35) = 13

d46 = min(d46, d43 + d36) = 4

d56 = min(d56, d53 + d36) = 8

La matriz de distancia después de esta iteración es:


4ª Iteración: nodo intermedio = 4

d12 = min(d12, d14 + d42) = 3

d13 = min(d13, d14 + d43) = 5

d15 = min(d15, d14 + d45) = 12

d16 = min(d16, d14 + d46) = 5

d23 = min(d23, d24 + d43) = 8

d25 = min(d25, d24 + d45) = 9

d26 = min(d26, d24 + d46) = 8

d35 = min(d35, d34 + d45) = 7

d36 = min(d36, d34 + d46) = 1

d56 = min(d56, d54 + d46) = 8

La matriz de distancia después de esta iteración es:

5ª Iteración: nodo intermedio = 5

d12 = min(d12, d15 + d52) = 3

d13 = min(d13, d15 + d53) = 5

d14 = min(d14, d15 + d54) = 1

d16 = min(d16, d15 + d56) = 5

d23 = min(d23, d25 + d53) = 8

d24 = min(d24, d25 + d54) = 4

d26 = min(d26, d25 + d56) = 8


d34 = min(d34, d35 + d54) = 6

d36 = min(d36, d35 + d56) = 1

d46 = min(d46, d45 + d56) = 4

La matriz de distancia después de esta iteración es:

6ª Iteración: nodo intermedio = 6

d12 = min(d12, d16 + d62) = 3

d13 = min(d13, d16 + d63) = 5

d14 = min(d14, d16 + d64) = 1

d15 = min(d15, d16 + d65) = 12

d23 = min(d23, d26 + d63) = 8

d24 = min(d24, d26 + d64) = 4

d25 = min(d25, d26 + d65) = 9

d34 = min(d34, d36 + d64) = 5

d35 = min(d35, d36 + d65) = 7

d45 = min(d45, d46 + d65) = 12

La matriz de distancia después de esta iteración es:


Ya se han hecho todas las iteraciones posibles. Por tanto, el camino mínimo entre
2 vértices cualesquiera del grafo será el obtenido en la matriz final. En este caso,
el camino mínimo entre 3 y 4 vale 5.
Bibliografía
http://micaminomaster.com.co/grafo-algoritmo/algoritmos-dijkstra-floyd-marshall/

https://es.wikipedia.org/wiki/Algoritmo_de_Floyd-Warshall

https://www.ecured.cu/Floyd-Warshall

https://estructurasite.wordpress.com/algortimo-de-floyd-warshall/

Cormen, Thomas H.; Leiserson, Charles E.; Rivest, Ronald L. (1990). Introduction
to Algorithms (1º Edición). Sección 26.2, "The Floyd–Warshall algorithm".

Floyd, Robert W. Algorithm 97: Shortest Path. Communications of the ACM.

Kleene, S. C. (1956 Representation of events in nerve nets and finite automata. En


C. E. Shannon and John McCarthy. Automata Studies.

Warshall, Stephen.A theorem on Boolean matrices.

Kenneth H. Rosen (2003). Discrete Mathematics and Its Applications, 5ª Edición.


Addison Wesley.

You might also like