Sie sind auf Seite 1von 90

Graphs

What is a graph?
• A data structure that consists of a set of nodes
(vertices) and a set of edges that relate the nodes
to each other
• The set of edges describes relationships among the
vertices
Formal definition of graphs

• A graph G is defined as follows:


G=(V,E)
V(G): a finite, nonempty set of vertices
E(G): a set of edges (pairs of vertices)
Directed vs. undirected graphs

• When the edges in a graph have no direction, the graph is called


undirected
Directed vs. undirected graphs (cont.)

• When the edges in a graph have a direction, the graph is called


directed (or digraph)

Warning: if the graph is


directed, the order of the
vertices in each edge is
important !!

E(Graph2) = {(1,3) (3,1) (5,9) (9,11) (5,7)


Trees vs graphs

• Trees are special cases of graphs!!


Graph terminology

• Adjacent nodes: two nodes are adjacent if they are connected by an


edge

• Path: a sequence of vertices that connect5 istwo


adjacent
nodestoin7 a graph
7 is adjacent from 5
• Complete graph: a graph in which every vertex is directly connected
to every other vertex
Graph terminology (cont.)
• What is the number of edges in a complete
directed graph with N vertices?
N * (N-1)

2
O( N )
Graph terminology (cont.)
• What is the number of edges in a complete
undirected graph with N vertices?
N * (N-1) / 2

2
O( N )
Graph terminology (cont.)
• Weighted graph: a graph in which each edge
carries a value
Graph implementation
• Array-based implementation
• A 1D array is used to represent the vertices
• A 2D array (adjacency matrix) is used to represent the edges
Array-based implementation
Graph implementation (cont.)
• Linked-list implementation
• A 1D array is used to represent the vertices
• A list is used for each vertex v which contains the
vertices which are adjacent from v (adjacency list)
Linked-list implementation
Adjacency matrix vs. adjacency list
representation
• Adjacency matrix
• Good for dense graphs --|E|~O(|V|2)
• Memory requirements: O(|V| + |E| ) = O(|V|2 )
• Connectivity between two vertices can be tested quickly
• Adjacency list
• Good for sparse graphs -- |E|~O(|V|)
• Memory requirements: O(|V| + |E|)=O(|V|)
• Vertices adjacent to another vertex can be found quickly
Graph specification based on adjacency
matrix representation
const int NULL_EDGE = 0;
private:
template<class VertexType> int numVertices;
class GraphType { int maxVertices;
public: VertexType* vertices;
GraphType(int); int **edges;
~GraphType(); bool* marks;
void MakeEmpty(); };
bool IsEmpty() const;
bool IsFull() const;
void AddVertex(VertexType);
void AddEdge(VertexType, VertexType, int);
int WeightIs(VertexType, VertexType);
void GetToVertices(VertexType, QueType<VertexType>&);
void ClearMarks();
void MarkVertex(VertexType);
bool IsMarked(VertexType) const; (continues)
template<class VertexType>
GraphType<VertexType>::GraphType(int maxV)
{
numVertices = 0;
maxVertices = maxV;
vertices = new VertexType[maxV];
edges = new int[maxV];
for(int i = 0; i < maxV; i++)
edges[i] = new int[maxV];
marks = new bool[maxV];
}

template<class VertexType>
GraphType<VertexType>::~GraphType()
{
delete [] vertices;
for(int i = 0; i < maxVertices; i++)
delete [] edges[i];
delete [] edges;
delete [] marks;
}
(continues)
void GraphType<VertexType>::AddVertex(VertexType vertex)
{
vertices[numVertices] = vertex;
for(int index = 0; index < numVertices; index++) {
edges[numVertices][index] = NULL_EDGE;
edges[index][numVertices] = NULL_EDGE;
}

numVertices++;
}

template<class VertexType>
void GraphType<VertexType>::AddEdge(VertexType fromVertex,
VertexType toVertex, int weight)
{
int row;
int column;

row = IndexIs(vertices, fromVertex);


col = IndexIs(vertices, toVertex);
edges[row][col] = weight;
}

(continues)
template<class VertexType>
int GraphType<VertexType>::WeightIs(VertexType fromVertex,
VertexType toVertex)
{
int row;
int column;

row = IndexIs(vertices, fromVertex);


col = IndexIs(vertices, toVertex);
return edges[row][col];
}
Graph searching

• Problem: find a path between two nodes of the graph (e.g., Austin
and Washington)
• Methods: Depth-First-Search (DFS) or Breadth-First-Search (BFS)
Depth-First-Search (DFS)

• What is the idea behind DFS?


• Travel as far as you can down a path
• Back up as little as possible when you reach a "dead end" (i.e., next vertex
has been "marked" or there is no next vertex)
• DFS can be implemented efficiently using a
stack
Depth-First-Search (DFS) (cont.)
Set found to false
stack.Push(startVertex)
DO
stack.Pop(vertex)
IF vertex == endVertex
Set found to true
ELSE
Push all adjacent vertices onto stack
WHILE !stack.IsEmpty() AND !found

IF(!found)
Write "Path does not exist"
start end

(initialization)
template <class ItemType>
void DepthFirstSearch(GraphType<VertexType> graph, VertexType
startVertex, VertexType endVertex)
{
StackType<VertexType> stack;
QueType<VertexType> vertexQ;

bool found = false;


VertexType vertex;
VertexType item;

graph.ClearMarks();
stack.Push(startVertex);
do {
stack.Pop(vertex);
if(vertex == endVertex)
found = true;

(continues)
else {
if(!graph.IsMarked(vertex)) {
graph.MarkVertex(vertex);
graph.GetToVertices(vertex, vertexQ);

while(!vertexQ.IsEmpty()) {
vertexQ.Dequeue(item);
if(!graph.IsMarked(item))
stack.Push(item);
}
}
} while(!stack.IsEmpty() && !found);

if(!found)
cout << "Path not found" << endl;
}
(continues)
template<class VertexType>
void GraphType<VertexType>::GetToVertices(VertexType vertex,
QueTye<VertexType>& adjvertexQ)
{
int fromIndex;
int toIndex;

fromIndex = IndexIs(vertices, vertex);


for(toIndex = 0; toIndex < numVertices; toIndex++)
if(edges[fromIndex][toIndex] != NULL_EDGE)
adjvertexQ.Enqueue(vertices[toIndex]);
}
Breadth-First-Searching (BFS)

• What is the idea behind BFS?


• Look at all possible paths at the same depth before you go at a deeper level
• Back up as far as possible when you reach a "dead end" (i.e., next vertex
has been "marked" or there is no next vertex)
Breadth-First-Searching (BFS) (cont.)
• BFS can be implemented efficiently using a queue
IF(!found)
Set found to false Write "Path does not exist"
queue.Enqueue(startVertex)
DO
queue.Dequeue(vertex)
IF vertex == endVertex
Set found to true
ELSE
Enqueue all adjacent vertices onto queue
WHILE !queue.IsEmpty() AND !found

• Should we mark a vertex when it is enqueued or


when it is dequeued ?
start end

(initialization)
next:
template<class VertexType>
void BreadthFirtsSearch(GraphType<VertexType> graph, VertexType
startVertex, VertexType endVertex);
{
QueType<VertexType> queue;
QueType<VertexType> vertexQ;//

bool found = false;


VertexType vertex;
VertexType item;

graph.ClearMarks();
queue.Enqueue(startVertex);
do {
queue.Dequeue(vertex);
if(vertex == endVertex)
found = true;

(continues)
else {
if(!graph.IsMarked(vertex)) {
graph.MarkVertex(vertex);
graph.GetToVertices(vertex, vertexQ);

while(!vertxQ.IsEmpty()) {
vertexQ.Dequeue(item);
if(!graph.IsMarked(item))
queue.Enqueue(item);
}
}
}
} while (!queue.IsEmpty() && !found);

if(!found)
cout << "Path not found" << endl;
}
Single-source shortest-path problem
• There are multiple paths from a source vertex to a destination vertex
• Shortest path: the path whose total weight (i.e., sum of edge weights)
is minimum
• Examples:
• Austin->Houston->Atlanta->Washington: 1560 miles
• Austin->Dallas->Denver->Atlanta->Washington: 2980 miles
Single-source shortest-path problem
(cont.)
• Common algorithms: Dijkstra's algorithm, Bellman-Ford algorithm
• BFS can be used to solve the shortest graph problem when the
graph is weightless or all the weights are the same
(mark vertices before Enqueue)
Paths and cycles

• A path is a sequence of nodes


v1, v2, …, vN such that (vi,vi+1)E for 0<i<N

• The length of the path is N-1.


• Simple path: all vi are distinct, 0<i<N

• A cycle is a path such that v1=vN


• An acyclic graph has no cycles

38
Cycles

BOS
DTW
SFO

PIT
JFK

LAX

39
Trees are graphs

• A dag is a directed acyclic graph.

• A tree is a connected acyclic undirected graph.

40
Example DAG
Undershorts
Socks
Watch
Pants Shoes
Shirt
a DAG implies an
ordering on events
Belt Tie

Jacket

41
Example DAG
Undershorts
Socks
Watch
Pants Shoes
Shirt
In a complex DAG, it
can be hard to find a
Belt Tie schedule that obeys
all the constraints.

Jacket

42
Topological Sort
Topological Sort

• For a directed acyclic graph G = (V,E)


• A topological sort is an ordering of all of G’s vertices v1, v2, …, vn such
that...

Formally: for every edge (vi,vk) in E, i<k.


Visually: all arrows are pointing to the right

44
Topological sort

• There are often many possible topological sorts of a given DAG


• Topological orders for this DAG :
• 1,2,5,4,3,6,7
• 2,1,5,4,7,3,6 1 2
• 2,5,1,4,7,3,6
• Etc.
3 4 5
• Each topological order is a feasible schedule.
6 7

45
Topological Sorts for Cyclic Graphs?

1 2
Impossible!
3

• If v and w are two vertices on a cycle, there


exist paths from v to w and from w to v.
• Any ordering will contradict one of these paths

46
Smallest path
Minimum Spanning Trees

56
Problem: Laying Telephone Wire

Central office

57
Wiring: Naïve Approach

Central office

Expensive!

58
Wiring: Better Approach

Central office

Minimize the total length of wire connecting the customers

59
Minimum Spanning Tree (MST)

A minimum spanning tree is a subgraph of an


undirected weighted graph G, such that

• it is a tree (i.e., it is acyclic)


• it covers all the vertices V
– contains |V| - 1 edges
• the total cost associated with tree edges is the
minimum among all possible spanning trees
• not necessarily unique

60
Kruskal’s Algorithm for Minimum Spanning
Tree
Applications of Depth First Search

1) For an unweighted graph, DFS traversal of the graph


produces the minimum spanning tree and all pair shortest
path tree.
2) Detecting cycle in a graph
A graph has cycle if and only if we see a back edge during
DFS. So we can run DFS for the graph and check for back
edges
3) Path Finding
We can specialize the DFS algorithm to find a path between
two given vertices u and z.
i) Call DFS(G, u) with u as the start vertex.
ii) Use a stack S to keep track of the path between the start
vertex and the current vertex.
iii) As soon as destination vertex z is encountered, return the
path as the
contents of the stack
4) Topological Sorting
Topological Sorting is mainly used for scheduling jobs from the given
dependencies among jobs. In computer science, applications of this
type arise in instruction scheduling, ordering of formula cell
evaluation when recomputing formula values in spreadsheets, logic
synthesis, determining the order of compilation tasks to perform in
makefiles, data serialization, and resolving symbol dependencies in
linkers
5) To test if a graph is bipartite
We can augment either BFS or DFS when we first discover a new
vertex, color it opposited its parents, and for each other edge, check
it doesn’t link two vertices of the same color. The first vertex in any
connected component can be red or black
6) Finding Strongly Connected Components of a graph A
directed graph is called strongly connected if there is a path from
each vertex in the graph to every other vertex.
7) Solving puzzles with only one solution, such as mazes
What are NP-complete

P is set of problems that can be solved by a deterministic Turing


machine in Polynomial time.
NP is set of decision problems that can be solved by a Non-
deterministic Turing Machine in Polynomial time. P is subset of
NP (any problem that can be solved by deterministic machine in
polynomial time can also be solved by non-deterministic
machine in polynomial time).
Informally, NP is set of decision problems which can be solved
by a polynomial time via a “Lucky Algorithm”, a magical
algorithm that always makes a right guess among the given set
of choices
Graph Coloring
Introduction

• When a map is colored, two regions with a


common border are customarily assigned
different colors.
• We want to use the smallest number of
colors instead of just assigning every
region its own color.
4-Color Map Theorem

• It can be shown that any two-dimensional


map can be painted using four colors in
such a way that adjacent regions (meaning
those which sharing a common boundary
segment, and not just a point) are different
colors.
Map Coloring

• Four colors are sufficient to color a map of the contiguous


United States.
Dual Graph

• Each map in a plane can be represented by a


graph.
– Each region is represented by a vertex.
– Edges connect to vertices if the regions
represented by these vertices have a common
border.
– Two regions that touch at only one point are not
considered adjacent.
• The resulting graph is called the dual graph
of the map.
Dual Graph Examples

B B
G A
C
A F C
D E
D

b E
b
c

a d f g a c e

e d
Graph Coloring

• A coloring of a simple graph is the


assignment of a color to each vertex of the
graph so that no two adjacent vertices are
assigned the same color.
• The chromatic number of a graph is the least
number of colors needed for a coloring of
the graph.
• What is the chromatic number of a bipartite
graph?
Example

• What is the chromatic number for each


of the following graphs?

White
White Yellow

Green Yellow
Yellow White

White Yellow Yellow White

Chromatic number: 2 Chromatic number: 3


Application

• The problem of coloring a graph arises in


many practical areas such as
pattern matching, sports scheduling,
designing seating plans, exam timetabling,
the scheduling of taxis, and solving
Sudoku puzzles