GRAPH ALGORITHM
Download
Report
Transcript GRAPH ALGORITHM
Nattee Niparnan
GRAPH ALGORITHM
Graph
A pair G = (V,E)
V = set of vertices (node)
E = set of edges (pairs of
vertices)
2
1
3
4
V = (1,2,3,4,5,6,7)
E=
((1,2),(2,3),(3,5),(1,4),(4,
5),(6,7))
6
5
7
Term you should already know
directed, undirected graph
Weighted graph
Bipartite graph
Tree
Spanning tree
Path, simple path
Circuit, simple circuit
Degree
Representing a Graph
Adjacency Matrix
A = |V|x|V| matrix
axy = 1
when there is an edge connecting
node x and node y
axy = 0
otherwise
1
2
3
4
5
2
1
3
4
5
1
2
3
0
1
0
1
0
1
0
1
1
0
0
1
0
0
1
4
5
1
1
0
0
1
0
0
1
1
0
Representing a Graph
Adjacency List
Use a list instead of a matrix
For each vertex, we have a linked list of their
neighbor
2
1
3
4
5
1
2
4
2
1
3
...
4
Representing a Graph
Incidences Matrix
Row represent edge
Column represent node
2
1
3
4
5
1
2
3
4
5
1
1
0
0
0
1
0
0
1
0
0
1
0
1
0
0
1
1
0
0
0
0
1
0
1
0
0
0
1
1
Depth First Search
Exploring a Maze
Exploring Problem
Input:
A Graph
Maybe as an adjacency matrix
A Starting node
Output:
List of node reachable from
Maybe as an array indexed by a node
Depth-First-Search
void explore(G, v)
// Input: G = (V,E) is a graph; v V
// Output: visited[u] is set to true for
all nodes u reachable from v
{
visited[v] = true
previsit(v)
for each edge (v,u) E
if not visited[u]
explore(u)
postvisit(v)
}
Example
Explore(A)
Extend to Graph Traversal
Traversal is walking in the graph
We might need to visit each component in the
graph
Can be done using explore
Do “explore” on all non-visited node
The result is that we will visit every node
What is the difference between just
looking into V (the set of vertices?)
Graph Traversal using DFS
void dfs(G)
{
for all v V
visited[v] = false
for all v V
if not visited[v]
explore(v)
}
Complexity Analysis
Each node is visited once
Each edge is visited twice
Why?
O( |V| + |E|)
Another Example
Another Example
Connected Component
Connectivity in Undirected
Graph
If
can reach
Then
If
can reach
can reach
&&
can reach
Then can reach
Also can reach
Divide
into smaller subset of vertices
that can reach each other
Connected Component Problem
Input:
A graph
Output:
Marking in every vertices identify the
connected component
Let it be an array ccnum, indexed by vertices
Solution
Define global variable cc
In previsit(v)
ccnum[v] = cc
Before calling each explore
cc++
DFS visiting time
Ordering in Visit
void previsit(v)
pre[v] = clock++
void postvisit(v)
post[v] = clock++
Ordering in Visit
•The interval for node u
is [pre(u),post(u)]
•The inverval for u,v is
either
•Contained
•disjointed
•Never intersect
DFS in Directed Graph
Type of Edge in Directed Graph
Directed Acyclic Graph (DAG)
A directed Graph without a cycle
Has “source”
A node having only “out” edge
Has “sink”
A node having only “in” edge
How can we detect that a graph is a DAG
What should be the property of “source” and
“sink” ?
Solution
A directed graph is acyclic if and only if it
has no back edge
Sink
Having lowest post number
Source
Having highest post number
Topological Sorting
Linearization of Graph
for DAG, we can have an ordering of node
Think of an edge as
Causality
Time-dependency
means
has to be done before
Linearization ordering of node by
causality
Linearization
One possible linearization
B,A,D,C,E,F
Order of work that can
be done w/o violating
the causality constraints
Topological Sorting Problem
Input:
A DAG (non-dag cannot be linearized)
Output:
A sequence of vertices
If we have a path from to
must come before in the sequence
Topological Sorting
Do DFS
List node by post number (descending)
3,8
4,5
2,9
6,7
1,12
10,11
Breadth First Search
Distance of nodes
The distance between two nodes is the
length of the shortest path between them
SA
1
SC
1
SB
2
DFS and Length
DFS finds all nodes reachable from the
starting node
But it might not be “visited” according to the
distance
Ball and Strings
We can compute distance by
proceeding from “layer” to “layer”
Shortest Path Problem (Undi,
Unit)
Input:
A graph, undirected
A starting node S
Output:
A label on every node, giving the distance
from S to that node
Breadth-First-Search
Visit node according to its layer
procedure bfs(G, s)
//Input: Graph G = (V,E), directed or undirected; vertex s V
//Output: visit[u] is set to true for all nodes u reachable from v
for each v V
visited[v] = false
visited[s] = true
Queue Q = [s]
//queue containing just s
while Q is not empty
v = Q.dequeue()
previsit(v)
visited[v] = true
for each edge (v,u) E
if not visited[u]
visited[u] = true
Q.enqueue(u)
postvisit(v)
Distance using BFS
procedure shortest_bfs(G, s)
//Input: Graph G = (V,E), directed or undirected; vertex s V
//Output: For all vertices u reachable from s, dist(u) is set
to the distance from s to u.
for all v V
dist[v] = -1
dist[s] = 0
Queue Q = [s] //queue containing just s
while Q is not empty
v = Q.dequeue()
for all edges (v,u) E
if dist[u] = -1
dist[u] = dist[v] + 1
Q.enqueue(u)
Use dist as
DFS by Stack
procedure dfs(G, s)
//Input: Graph G = (V,E), directed or undirected; vertex s V
//Output: visited[u] is true for any node u reachable from v
for each v V
visited[v] = false
visited[s] = true
Stack S = [s]
//queue containing just s
while S is not empty
v = S.pop()
previsit(v)
visited[v] = true
for each edge (v,u) E
if not visited[u]
visited[u] = true
S.push(u)
postvisit(v)
DFS vs BFS
DFS goes depth first
Trying to go further if possible
Backtrack only when no other possible way to
go
Using Stack
BFS goes breadth first
Trying to visit node by the distance from the
starting node
Using Queue