You are on page 1of 19

Algoritmos Elementales de Grafos Breadth-first search Depth-first search Orden topolgico Componentes fuertemente conexas

Agustn J. Gonzlez ELO-320: Estructura de Datos y Algoritmos

Introduccin


Muchas situaciones se pueden modelar a travs de grafos. Por ejemplo una lista de actividades las cuales tiene dependencia unas de otras. No puedo ponerme la correa antes que el pantaln. Para detectar si hay vas de un solo sentido que conducen a caminos sin salida. En la solucin de estos problemas los mecanismos de recorrido de los nodos del rbol son importantes. Existen dos formas bsicas: Recorrido por cercana a un nodo dado (avanzar parejo en todas las lneas) o Breadth-first search y recorrido en profundidad (recorre todo un camino y luego explora otros) o Depth-first search.
(Breadth: ancho, anchura; amplitud. En un rbol la idea es recorrerlo hacia lo ancho primero.) (Depth: Profundidad) 2

 

Introduccin (cont)


 

Estudiaremos mtodos para representar y explorar o recorrer grafos. Explorar un grafo significa seguir sistemticamente los arcos de un grafo para visitar sus vrtices. Las dos representaciones ms comunes para representar grafos son: Lista de adyacencia y matriz de adyacencia. Representacin de grafos Un Grafo G =(V, E) , V : conjunto de vrtices y E conjunto de arcos, se representa preferiblemente con una Lista de adyacencia porque sta permite una representacin compacta cuando el grafo es disperso; i.e. cuando |E| << |V|2 Es preferible usar una representacin con Matriz de Adyacencia cuando el grafo es denso; i.e. |E| ~ |V|2,.o cuando es preciso saber rpidamente si hay un arco conectando dos vrtices.
3

Representacin con Listas de Adyacencia




En este caso el Grafo G=(V, E) consiste de un arreglo Adj que almacena |V| listas, una para cada vrtice en V. Para cada u V, la lista de adyacencia Adj[uA contiene (punteros a) todos los vrtices v tal que hay una arco (u,v) E. Si el grafo es dirigido, se cumple que la suma de los largos de las listas de adyacencia es |E|. Si el grafo no es dirigido, se cumple que la suma de los largos de las listas de adyacencia es 2*|E|. Dado que cada arco aparece dos veces. En cualquier caso, la memoria requerida es O(max(|V|,|E|)) = O(|V|+|E|). 4

Representacin con Listas de Adyacencia: Ejemplo




Caso grafo no dirigido


1 2 3 5 4

1 2 3 4 5
1

2 1 2 5 2

5 5 4 2 4

4 3 1

4 2 1 2 3 5 2 6 5  Caso Grafo dirigido 3 2 4 6 4 5 5 4 6 6 Las listas de adyacencia pueden ser fcilmente adaptadas para representar grafos con peso. En stos un peso es asociado a cada arco a travs de una funcin de peso w: E --> R. As el peso del arco (u,v) es puesto en el nodo v de la lista u.

Representacin con Matriz de Adyacencia: Ejemplo




Caso grafo no dirigido


1 2 3 5


1 2 3 4 5

1 2 3 4 5

0 1 0 0 1

1 0 1 1 1

0 1 0 1 0

0 1 1 0 1

1 1 0 1 0

Notar la simetra. Para ahorrar memoria se puede almacenar slo la mitad.


1 2 3 4 5 6 1 2 3

Caso grafo dirigido


1 2 3 4 5 6

Si el grafo es con peso, el peso se almacena en la matriz. Cuando un arco no existe se toma algn valor que represente su ausencia 0, -1 etc. Dependiendo de la aplicacin. La matriz de adyacencia es preferible cuando el grafo es pequeo por su simplicidad.

0 0 0 0 0 0

1 0 0 1 0 0

0 0 0 0 0 0

1 0 0 0 1 0

0 1 1 0 0 0

0 0 1 0 0 1

Algoritmos de Exploracin de un grafo.


 

La idea es visitar todos los vrtices siguiendo los arcos. Breadth-first search bsqueda (visitar) primero por distancia (todos de igual distancia se visitan primero) Dado un vrtice fuente s, Breadth-first search sistemticamente explora los arcos del grafo G para descubrir todos los vrtices alcanzables desde s. Tambin calcula la distancia (menor nmero de arcos) desde s a todos los vrtices alcanzables. Tambin produce un rbol con raz en s y que contiene a todos los vrtices alcanzables. El camino desde s a cada vrtice en este recorrido contiene el mnimo nmero de arcos. Es el camino ms corto medido en nmero de vrtices. Su nombre se debe a que expande uniformemente la frontera entre lo descubierto y lo no descubierto. Llega a los nodos de distancia k, slo luego de haber llegado a todos los nodos a distancia k-1. 7

Algoritmos Breadth-first search (BFS)




Inicialmente el algoritmo colorea los vrtices con blanco. Luego stos pasan a plomo y luego negro. El color plomo es usado para definir la frontera entre lo ya descubierto o explorado y lo por visitar. BFS(G,s) { /* pseudo-cdigo */ int d[N], p[N], color[N]; /* Arreglos de distancia, de padres, y de color */ QUEUE Q; /* Cola usada como estructura auxiliar */ for ( cada vrtice u V[G] -{s}) { color [u] =Blanco; d[u] = g; /* distancia infinita si el nodo no es alcanzable */ } color[s] =Plomo; d[s] = 0; p [s]=NULL; Enqueue(Q, s); while ( !Queue_Vaca(Q) ) { u = Cabeza(Q); /* u es el primer nodo de la cola */ for ( cada v Adj [u] ) { if (color [v] == Blanco) { color[v]=Plomo; /* Plomo al entrar a la cola */ d [v]=d [u] +1; p [v] = u; Enqueue(Q, v); } Dequeue(Q); /* se extrae u */ color [u] = Negro; /* negro luego de salir de la cola */ } } El tiempo de ejecucin es O(|V|+|E|). Notar que cada nodo es encolado una vez y su lista de adyacencia es recorrida una vez tambin.

Ejemplo de Breadth-first search Recorrido o Bsqueda de nodos en amplitud


r
(a)

g g
v r

g
x t

g g
y u

1
Q s 0 (b)

g g
t x

g g g g
3
y u y u

g
0 1

w s

g
2 2
x t

g
1
(d)

1
w s

w r 1 1

v r

1
(c)

g g
y u

g
v r

r t x 1 2 2

0 1
w s

2 2
t x

2
v r

t x v 2 2 2

w s

1
(e)

0 1
w s

2 2
x t

2
v r

g
y u

x v u 2 2 3

1
(f)

0 1
w s

2 2
t x

2
v r

3
y u

v u y 2 3 3

1
(g)

0 1
w s

2 2
x t

3
Q

1
u y 3 3 (h)

0 1
w

2 2
x

3 3
y

y 3

2
v r

3
y u

2
v

1
(i)

0 1
w

2 2
x

3
Q

2
v

3
y

Algoritmos Depth-first search (DFS)


 

Como en BFS, inicialmente el algoritmo colorea los vrtices con blanco. Luego stos pasan a plomo y luego negro. En DFS el color plomo es usado para definir nodos cuyos descendientes estn siendo visitados. int tiempo; /* global */ int d[N], f[N], p[N], color[N]; /* Arreglos de tiempo de entrada, tiempo de salida, padres, y color */ DFS(G) { /* pseudo-cdigo */ for ( cada vrtice u V[G]) { color [u] =Blanco; p[u] = NULL; } tiempo = 0; for (cada vrtice u V[G]) if (color[u] == Blanco) DFS_visit(u); } DFS_visit (u) /* pseudo-cdigo */ color [u]= Plomo; /* Vrtice Blanco u es visitado, ingresamos a su sub-rbol */ d[u] = ++tiempo; /* el tiempo avanza cada vez que entramos o salimos de un nodo*/ for ( cada v Adj [u] ) { /* explora arcos (u,v) */ if (color [v] == Blanco) { /* v no ha sido visitado */ p [v] = u; /* u es el padre de v, se lleg a v va u. */ DFS_visit(v); } } color [u] = Negro; /* ennegrezca u, salimos de su sub-rbol */ f [u] = ++tiempo; } El tiempo de ejecucin de DFS es tambin O(|V|+|E|). Cada arco y nodo es recorrido una vez.

10

Ejemplo de DFS
(a) u 1/ v w (b) u 1/ v 2/ w (c) u 1/ v 2/ w (d) u 1/ v 2/ w 3/ y v 2/ 4/ x (h) u 1/ 3/ y v 2/7

x (e) u 1/

y v 2/

z w

x (f) u 1/

y v 2/

z w

x (g) u 1/

z w

z w

4/ x (i) u 1/

3/ y v 2/7

z w

4/5 x (j) u 1/8

3/ y v 2/7

z w

4/5 x (k) u 1/8

3/6 y v 2/7

z w 9/ (l)

4/5 x u 1/8

3/6 y v 2/7

z w 9/

4/5 x (m) u 1/8

3/6 y v 2/7

z w 9/

4/5 x (n) u 1/8

3/6 y v 2/7

z w 9/

4/5 x (o) u 1/8

3/6 y v 2/7

z w 9/

4/5 x (o) u 1/8

3/6 y v 2/7

z w 9/12

4/5 x

3/6 y

10/ z

4/5 x

3/6 y

10/ z

4/5 x

3/6 y

10/11 z

4/5 x

3/6 y

10/11 z 11

Orden Topolgico


Orden topolgico de un DAG G=(V,E) es un orden lineal de todos los vrtices tal que si G contiene el arco (u,v), entonces u aparece antes que v en el orden. El orden topolgico tiene sentido slo en grafos acclicos dirigidos (DAG). Cuando se tienen muchas actividades que dependen parcialmente unas de otras, este orden permite definir un orden de ejecucin sin conflictos. Grficamente se trata de poner todos los nodos en una lnea de manera que slo haya arcos hacia delante. Algoritmo:


Topological_Orden(G) Llamar a DFS(G) para calcular el tiempo de trmino f[v] para cada vrtice. Listar los nodos en orden decreciente de tiempo de trmino. 12

Ejemplo: Orden topolgico


11/16

calzoncillo

calcetines 17/18 zapatos


13/14

12/15 pantaln 6/7

reloj

9/10

correa

camisa 1/8 corbata chaqueta


3/4 2/5

calcetines 17/18

calzoncillo 11/16

pantaln 12/15

zapatos 13/14

reloj 9/10

camisa 1/8

correa 6/7

corbata 2/5

chaqueta 3/4

Es ste el nico orden topolgico?


13

Ejemplo: Orden topolgico

Cul es el orden topolgico?

14

Deteccin de componentes fuertemente Conexas




 

Una componente fuertemente conexa de un grafo G=(V,E) es el mximo conjunto de vrtices U subconjunto de V tal que para cada par de vrtices u, v en U, existan caminos desde u a v y viceversa. El algoritmo descubre todas las componentes fuertemente conexas. Para ello define el grafo traspuesto de G, GT= (V,ET), donde ET={(u,v) tal que (v,u) pertenece a E}. En otras palabras, invierte el sentido de todas los arcos. Algoritmo: Strongly_Connected_Components(G) 1.- Llamar a DFS(G) para obtener el tiempo de trmino f[u], para cada vrtice u; 2.- Calcular GT; 3.- Llamar a DFS(GT), pero en el loop principal de DFS, considerar los vrtices en orden decreciente de f [u]. 4.- La salida son los vrtices de cada rbol de la foresta del paso 3. Cada rbol es una componente fuertemente conexa separada.

15

Ejemplo de Deteccin de Componentes fuertemente conexas


a b c d

13/14

11/16

1/10

8/9

12/15
e

3/4
f a

2/7
g b

5/6
h c d

cd abe fg h 16

Por qu funciona?


 

No haremos una demostracin rigurosa, pero si daremos algunos elementos que ayudan a su entendimiento. Cuando se recorre un grafo en DFS se tiene: si v es un descendiente de u entonces f[v]<f[u]. (i.e. Los descendientes terminan primero.) Lo contrario no necesariamente es vlido. Si v es descendiente de u, v es alcanzable desde u. La conectividad de nodos en una componente conexa es invariante con respecto a la inversin de arcos. Si de v llegamos a u, y de u llegamos a v, al invertir los arcos esta propiedad se mantiene. Al iniciar nuestro recorrido usando orden de trmino decreciente, estaremos partiendo por nodos en distintas componentes (dado que otra manera seran descendientes). Al hacer el recorrido en orden inverso (GT) llegaremos a todos los de la componente conexa, pero no a aquellos de otras.
17

Por qu funciona? Continuacin...




Si tenemos que C y C son dos componentes fuertemente conexas, y adems hay un arco de C a C, entonces no puede haber un arco de C a C.
C C

Si existiera el arco de vuelta C y Cseran slo una componente fuertemente conexa.

18

Por qu funciona? Continuacin...




Si tenemos que C y C son dos componentes fuertemente y un arco (u,v) que va de una a otra, entonces f[u] > f[v].
C u f[u] > f[v] v C

Si partimos el recorrido en algn nodo de C, naturalmente v ser alcanzado despus que u y por ello su f[v] ser menor. Si partimos el recorrido en algn nodo de C, f[v] ser menor que todos los f de los nodos visitados luego en C.

Entonces al cambiar las flechas, y partir por mayores f[u], podremos distinguir las componentes fuertemente conexas.
C u f[u] > f[v] 19 v C

You might also like