Está en la página 1de 35

GRAFOS

Estructuras de Datos
CCPG1006
MATRIZ DE CAMINOS

Es una matriz cuadrada P que representa si hay o no


camino entre dos vértices Vi y Vj

1, si entre Vi y Vj hay camino


Pij 
0, si no lo hay
CIERRE TRANSITIVO

• Es el grafo resultante de la matriz de caminos


• Si un grafo es fuertemente conexo
Su cierre transitivo es un grafo completo
MATRIZ DE CAMINOS UN POSIBLE ALGORITMO

A B C D E
A
B
mAdyacencia : A =
C
D
E
• Entre Vi y Vj puede haber camino
• Directo, cuando A[i][j] == 1, camino de long. 1
• O pasando por otros vértices
• Si solo analizamos pasar por un Vk extra
• Cuando A[i][k] == 1 && A[k][j] == 1, long. 2
• Si Vk puede ser V1 o V2 o … Vn, realmente se tiene:
(A[i][1] && A[1][j]) || (A[i][2] && A[2][j]) || … (A[i][n] && A[n][j])
MATRIZ DE CAMINOS UN POSIBLE ALGORITMO

(A[i][1] && A[1][j]) || (A[i][2] && A[2][j]) || (A[i][n] && A[3][n])


A B C D E
A
B
C
D
A B C D E
A 0 0 1 0 1
B 1 0 0 0 0
C 0 1 0 0 0 = A2
D 0 1 1 0 1
E 0 0 0 0 0
MATRIZ DE CAMINOS UN POSIBLE ALGORITMO

A camino de long. 1
A2 = A * A camino de long. 2
A3 = A2 * A camino de long. 3
……

An= An-1* A camino de long. n


A B C D E
A 1 1 1 0 1
B 1 1 1 0 1
Matriz de caminos :
C 1 1 1 0 1
P = A + A2 + A3 + A4 +…. An D 1 1 1 0 1
E 0 0 0 0 0
WARSHALL: MAS EFICIENTE

• El anterior algoritmo es poco eficiente, peor cuando el grafo


tiene muchos vértices
• Warshall propuso otro algoritmo más eficiente
– Calcular una secuencia de matrices cuadradas
• De 0s(no hay camino) y 1s(hay camino)
• P0, P1, P2, P3… PN
– La diferencia entre Pk y Pk-1
• Se basa añadir un vértice Vk-1 al análisis
• Para saber si a través de Vk-1 hay camino entre Vi y Vj
COMO FUNCIONA

Existe una matriz inicial P0


Indica si hay o no camino DIRECTO de Vi a Vj
La matriz que le sigue P1
Indica si : Hay o no camino DIRECTO (Esto ya lo sabe P0)
O pasando por V0 (añade este vértice al análisis)
P2
Indica si: Hay camino DIRECTO o pasando por V0 (Esto ya lo sabe P1)
O pasando por V1
P3
Indica si: Hay camino DIRECTO o pasando por V0, o V1 (Lo sabe P2)
O pasando por V2
Pk
Indica: Lo que ya sabe Pk-1
O pasando por Vk-1
ENTONCES

Debemos encontrar Pn
– Sabiendo que Pk[i][j] es 1 si
• Pk-1[i][j] es 1 o En cada paso se incorpora un nuevo vértice, a
los anteriores para poder formar camino.
• Pk-1[i][k] && Pk-1[k][j]
• En otras palabras:

 1, si Pk - 1[i][j]  (Pk - 1[i][k]  Pk - 1[k][j])


Pij 
0, si no
IMPLEMENTADO

public static int [][] matrizCaminos(GrafoMatriz g) {


int n = g.numeroDeVertices();
int [][] P = new int[n][n]; // matriz de caminos
// Se obtiene la matriz inicial: matriz de adyacencia
for (int i = 0; i < n; i++)
for (int j = 0; j < n; j++)
P[i][j] = g.adyacente[i,j];

for (int k = 0; k < n; k++){


for (int i = 0; i < n; i++){
for (int j = 0; j < n; j++){
P[i][j]= P[i][j] || (P[i][k] && P[k][j]);
}
}
}
Coste: O (n3) matriz de adyacencia
return P; 2
O (n +n) lista de adyacencia
}
WARSHALL IMPLEMENTADO
A B C D E
A 0 1 0 0 0
B 0 0 1 0 1
C 1 0 0 0 0
D 1 1 0 0 1
E 0 0 0 0 0

A B C D E
A 0 1 0 0 0
 1, si Pk - 1[i][j]  (Pk - 1[i][k]  Pk - 1[k][j]) B 0 0 1 0 1
Pij 
0, si no C 1 1 0 0 0
D 1 1 0 0 1
0 0 0 0 0
E
WARSHALL IMPLEMENTADO
A B C D E
A 0 1 1 0 1

B 0 0 1 0 1
C 1 1 1 0 1
D 1 1 1 0 1
0 0 0 0 0
E
A B C D E
A 1 1 1 0 1
B 1 1 1 0 1
C 1 1 1 0 1
D 1 1 1 0 1
E 0 0 0 0 0
WARSHALL IMPLEMENTADO
A B C D E
A 1 1 1 0 1
B 1 1 1 0 1
C 1 1 1 0 1
D 1 1 1 0 1
E 0 0 0 0 0

1 1 1 0 1
1 1 1 0 1
P= 1 1 1 0 1
1 1 1 0 1
0 0 0 0 0
CAMINOS MAS CORTOS

• Frecuentemente, se desea conocer en una red


– Cuál es el camino más corto entre un par de vértices
– En este caso
• Si importa cuántos caminos existen
• Si ya se conoce un camino, pero existe uno mejor,
sustituir
• Se aplica el algoritmo de Dijkstra
– Resuelve el problema en pasos sucesivos
– En cada paso selecciona la solución más óptima
DIJKSTRA
• Dado un V0, Dijkstra busca un conjunto D con
– Las menores distancias de V0 al resto de vértices
• Al inicio, solo conocemos
– Las distancias de los adyacentes
– D es inicializada a:
• Factor de peso para los adyacentes, Infinito para los no adyacentes
• D va ser mejorado sucesivamente
– Escogiendo el vértice Vk no elegido antes
• Que tenga la distancia más corta V0, Vk
– Probamos si pasando por Vk
• Se puede obtener distancias mas cortas de las que tenemos para
cada Vértice restante del grafo
Pasando por V3,
EJEMPLO DE DIJKSTRA
D[v2] + Pesos[v2][v5]) < D[v5]

Pasando por V2, Distancia de V1


Distancia de V1 a V5
seria 7, CAMBIAR
a V5 sería 8, no hay mejora V1 V2 V3 V4 V5 V6

Visitados Vertice D[0] D[1] D[2] D[3] D[4] D[5]


Evaluado
De V1 AL RESTO V1 V1 0 3 4 ∞ 8 ∞
5 V1,V2
V2 V5 V2 0 3 4 ∞ 8 ∞
3
3 V1,V2,V3 V3 0 3 4 ∞ 7 ∞
8
V6 V1,V2,V3,V5 V5 0 3 4 14 7 10
V1 7 0 3 4 12 7 10
V1,V2,V3,V5,V6 V6
3
4 V3 V4 2 V4 0 3 4 12 7 10
Ultimo: V1 V1 V1 V1
V6 V1
V5 V3 V1
V5

1. D[] se incializa con F.P. de adyacentes al origen

2. Escoger vértice Vk que no haya sido visitado, Repetir hasta k se hayan


con la menor distancia del Vevaluado a Vk visitado todos los vertices
3. Revisar si alguna distancia puede ser mejorada
pasando por Vk
D[Vevaluado] + Pesos[Vevaluado][Vj]) < D[Vj]
Para todos los adyacentes j del Vevaluado
DIKSTRA

1. Se crea una lista de VDis con todos los vértices del grafo,
y cada VDis creado se guarda en una lista
2. Se saca de la lista el menor VDis por distancia(vmenor)
3. Por cada VDis v de la lista, se revisa:
Si su vértice es adyacente al vértice de vmenor y si
pasando por vmenor se puede conseguir una mejor
distancia. Si es así, se modifica v con los nuevos datos
4. Se repite todo desde el paso 2 hasta que no haya nada en
la lista
DIKSTRA V1 V2 V3 V4 V5 V6

Visitados Vertice D[0] D[1] D[2] D[3] D[4] D[5]


Evaluado
V1 0 3 4 ∞ 8 ∞

Ultimo: V1 V V1 V1
V1 V1 V1

Coste: O (n2) matriz de adyacencia


O(n log(n) + log(n)) lista de ady.
DIKSTRA
DIKSTRA

De V1 AL RESTO
V1 V2 V3 V4 V5 V6
V2 V5
3 5
3 0 3 4 12 7 10
8 Distancia:
V6
V1 7 Ultimo: V1 V1 V1 V6 V3 V5
3
4 V3 V4 2
CAMINOS MAS CORTOS ENTRE TODOS LOS
PARES DE VERTICES

• Es una generalización de lo anterior


• Si se puede obtener la menor distancia
– De un V0 al resto
• También se puede obtener
– La menor distancia de todos los vértices al resto
• Se podría aplicar Dijkstra
– A cada vértice
– Y obtener n vectores D, o , una matriz F
• Pero se puede aplicar otro algoritmo
FLOYD - WARSHALL
• Este algoritmo se basa en Warshall
– Se calculaba una secuencia de matrices Pk
– Cada Pk evaluaba dos opciones
• Que Pk-1 indicara camino entre Vi y Vj o
• Que Pk-1 indicara camino entre Vi y Vj Pasando por Vk
• Floyd también calcula Fk (visitados), pero
– Cada Fk escogerá la menor distancia entre
• Distancia entre Vi y Vj, indicado por Fk-1 o
• Distancia entre Vi y Vj pasando por Vk, indicado por Fk-1

Fij  Min(F k-1[i][j] ,(Fk-1[i][k]  Fk-1[k][j]))


FLOYD - WARSHALL

D=

0 0 0 0 0
1 1 1 1 1
C= 2 2 2 2 2
D=
3 3
0 3 3 3
4 4 4 4 4
FLOYD - WARSHALL

D=

0 0 0 1 1
1 1 1 1 1
C= 2 2 2 1 2 D=
3 0 3 3 3
4 4 4 4 4
FLOYD - WARSHALL

D=

0 0 0 1 3
3 1 1 1 3
C= 2 2 2 1 2 D=
3 0 3 3 3
3 3 4 4 4
ARBOL DE EXPANSION DE COSTE MINIMO

• Dado un grafo G
– No dirigido
– Valorado, con pesos no negativos
• El árbol de expansión mínima
– Es un grafo parcial conexo a partir de G
– Tal que la suma de sus aristas sea mínima
• Ejemplo de aplicación
– Redes de comunicaciones, de costo mínimo
ALGORITMO DE PRIM

• Dado el grafo, se debe seleccionar


– Un vértice de inicio v
• Dicho vértice v se añade a un conjunto W
• Escoger el vértice u que no pertenezca a W
– Adyacente a cualquiera de los vértices de W
– Y que tenga un costo mínimo
• Añadir el vértice u al conjunto W
• Repetir proceso hasta que V == W
EJEMPLO

Desde 1
1 2
1 2 3

6 4
4 6
5

4 3 5 8 6

7
4 3

W= 1 ,2 ,3 ,4 ,5 ,7 ,6
EJEMPLO

1 2
1 2 3

4 3 5 6

4 3

W= 1 ,2 ,3 ,4 ,5 ,7 ,6
EJERCICIO PRIM
ALGORITMO DE KRUSKAL

• Kruskal se basa en el concepto de


– Componentes conexas
• Sabemos que en el árbol de expansión
– Deben aparecer todos los vértices de G
• Lo que no sabemos aún
– Es que arcos escoger para unirlos
• Lo que a Kruskal le interesara elegir
– Son los arcos, no los vértices, como en Prim
COMO FUNCIONA

• Primero añadir todos los vértices al árbol A


– Estos forman n componentes conexas
• Luego elegir el arco de costo mínimo
• Que no haya sido elegido anteriormente y que
• No una dos vértices de una misma componente
• Este proceso se repite hasta que
– Se hayan unido todos los vértices
– Es decir, n-1 veces
KRUSKAL

1 1 2 2 3 1 2 3
6 5
4 4 6
3 8
4 5 6 4 5 6

7
4 3
7 7
KRUSKAL
EJERCICIO ARBOL DE EXPANSION DE COSTE
MINIMO

También podría gustarte