39
Chapter 28 Graphs and Applications Part1. Non-weighted Graphs CIS265/506 Cleveland State University Prof. Victor Matos Adapted from: Introduction to Java Programming: Comprehensive Version, Eighth Edition by Y. Daniel Liang

Chapter 30 Graphs and Applications - Department of Computer

  • Upload
    others

  • View
    1

  • Download
    0

Embed Size (px)

Citation preview

Chapter 28

Graphs and Applications

Part1. Non-weighted Graphs

CIS265/506 Cleveland State University – Prof. Victor Matos Adapted from: Introduction to Java Programming: Comprehensive Version, Eighth Edition by Y. Daniel Liang

Modeling Using Graphs

Seattle

San Francisco

Los Angeles

Denver

Chicago

Kansas City

Houston

Boston

New York

Atlanta

Miami

Dallas

2

Weighted Graph Animation

3

www.cs.armstrong.edu/liang/animation/GraphLearningTool.html

Seven Bridges of Königsberg

4

Island 1 Island 2

B

A

C D

A

C

B

D

The city, islands, and bridge could be

abstracted as a graph holding vertices and

edges (bridges).

The problem was to find a walk through

the graph that would begin and end at the

same vertex crossing each edge exactly once.

The city of Konigsberg is

connected to two islands

through seven bridges.

Seven Bridges of Königsberg

5

A, 3

C, 5

B, 3

D, 3

No solution!!

Def. A path that traverses all bridges

once and also has the same starting and

ending is called an Eulerian circuit.

Such a circuit exists if, and only if, the

graph is connected, and there are no nodes

of odd degree at all.

A node degree is the count of edges

adjacent to the node.

Leonhard Euler, 1707

Basic Graph Terminology

6

1. What is a graph?

2. Directed vs. undirected graphs

3. Weighted vs. non-weighted graphs

4. Adjacent vertices

5. Incident

6. Degree

7. Neighbor

8. loop

Leonhard Euler, 1707-1785

Basic Graph Terminology

7

1. What is a graph?

A graph G(V, E) is a representation

of a set of vertices V and edges E.

Two vertices v1 and v2 in V are related

iff there is and edge e12 in E connecting

v1 and v2. Leonhard Euler, 1707-1785

Seattle

San Francisco

Los Angeles

Denver

Chicago

Kansas City

Houston

Boston

New York

Atlanta

Miami

Dallas

Basic Graph Terminology

8

1. What is

a graph?

Basic Graph Terminology

9

2. Node, vertice, vertex

3. Parallel edge

4. Loops

5. Complete graph

6. Simple graph

(connected, undirected,

no loops, no parallel

weighted)

Basic Graph Terminology

10

7. Spanning tree T of a connected, undirected graph G is a tree

composed of all the vertices and some (or perhaps all) of the

edges of G.

A graph may have several

Spanning trees !

Java: Representing Graphs

11

Representing

Vertices

Representing Edges:

Edge Array

Edge Objects (POJO)

Adjacency Matrices

Adjacency Lists

Representing Vertices

12

String[ ] vertices = {“Seattle“, “San Francisco“, … };

City[ ] vertices = {city0, city1, … };

public class City {

private String cityName;

private int population; ...

}

List<String> vertices;

Seattle

San Francisco

Los Angeles

Denver

Chicago

Kansas City

Houston

Boston

New York

Atlanta

Miami

Dallas A vertex could be an object of any type.

Representing Edges: Edge Array

13

int[][] edges = {{0, 1}, {0, 3} {0, 5}, {1, 0}, {1, 2}, … };

There is an edge

between city0 and city1

Representing Edges: Edge Object

public class Edge {

int v1, v2;

public Edge(int v1, int v2) {

this.v1 = v1;

this.v 2 = v2;

}

List<Edge> list = new ArrayList<Edge>();

list.add( new Edge(0, 1) );

list.add( new Edge(0, 3) ); …

Representing Edges: Adjacency Matrix

15

int[][] adjacencyMatrix = { {0, 1, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0}, // Seattle {1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0}, // San Francisco {0, 1, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0}, // Los Angeles {1, 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0}, // Denver {0, 0, 1, 1, 0, 1, 0, 1, 1, 0, 1, 0}, // Kansas City {1, 0, 0, 1, 1, 0, 1, 1, 0, 0, 0, 0}, // Chicago {0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0}, // Boston {0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0}, // New York {0, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 1}, // Atlanta {0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1}, // Miami {0, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1}, // Dallas {0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0} // Houston };

Entry adjacencyMatrix[i][j] is 1 if there is an edge connecting

city-i and city-j

Representing Edges: Adjacency List

16

neighbors[0]

neighbors[1]

neighbors[2]

neighbors[3]

neighbors[4]

neighbors[5]

neighbors[6]

neighbors[7]

neighbors[8]

neighbors[9]

neighbors[10]

neighbors[11]

Seattle

San Francisco

Los Angeles

Denver

Kansas City

Chicago

Boston

New York

Atlanta

Miami

Dallas

Houston

1 3 5

0 2 3

0 1 2 4 5

1 3 4 10

2 3 5 7 8 10

0 3 4 7 11

5 7

4 5 6 8

4 7 9 10 11

8 11

2 4 8 11

10 8 9

List<Integer>[ ] neighbors = new LinkedList<Integer>[12];

Graph

WeightedGraph

AbstractGraph

UnweightedGraph

Interface Abstract Class Concrete Classes

Modeling Graphs

17

In a style similar to the Java Collection Framework we will define

1. an interface named Graph that contains all common operations

of graphs and

2. an abstract class named AbstractGraph that partially

implements the Graph interface.

3. Many concrete graphs may be added to the design. For example,

we will define such graphs named UnweightedGraph and

WeightedGraph.

Modeling

Graphs

18

Modeling

Graphs

19

Graph Traversals - Trees

20

Depth-first search (DFS) and breadth-first search (BFS)

Both traversals result in a spanning tree, which can be modeled using a class.

Depth-First Search (DFS)

21

1. In the case of a tree, DFS search starts from the root (similar

to pre-order navigation).

2. In a graph, the search can start from any vertex.

dfs(vertex v) {

visit v;

for each neighbor w of v

if (w has not been visited) {

dfs(w);

}

}

DFS Depth-First Search Example

22

0 1

2

3 4

0 1

2

3 4

0 1

2

3 4

0 1

2

3 4

0 1

2

3 4

Begin at node 0

Seattle

San Francisco

Los Angeles

Denver

Chicago

Kansas City

Houston

Boston

New York

Atlanta

Miami

Dallas

DFS Depth-First Search Example

23

Applications of the DFS

24

1. Detecting whether a graph is connected. Search the graph

starting from any vertex. If the number of vertices searched is the same

as the number of vertices in the graph, the graph is connected.

Otherwise, the graph is not connected

2. Detecting / finding a path between two vertices.

3. Finding all connected components. A connected component is a

maximal connected subgraph in which every pair of vertices are

connected by a path.

4. Detecting / Finding a cycle in a graph.

Breadth-First Search (BFS)

25

With breadth-first traversal of a tree, the nodes are visited level

by level.

1. First the root is visited,

2. then all the children of the root,

3. then the grandchildren of the root from left to right,

4. and so on.

BFS Breadth-First Search Algorithm

26

bfs(vertex v) {

create an empty queue for storing vertices to be visited;

add v into the queue;

mark v visited;

while the queue is not empty {

dequeue a vertex, say u, from the queue

process u;

for each neighbor w of u

if w has not been visited {

add w into the queue;

mark w visited;

}

}

}

BFS Breadth-First Search Example

27

0 1

2

3 4

0 1

2

3 4

0 1

2

3 4

Queue: 0

Queue: 1 2 3

Queue: 2 3 4

isVisited[0] = true

isVisited[1] = true

isVisited[2] = true

isVisited[3] = true

isVisited[4] = true

BFS Breadth-First Search Example

Seattle

San Francisco

Los Angeles

Denver

Chicago

Kansas City

Houston

Boston

New York

Atlanta

Miami

Dallas

28

Applications of the BFS

29

1. Detecting whether a graph is connected. A graph is connected if there is a path

between any two vertices in the graph.

2. Detecting whether there is a path between two vertices.

3. Finding a shortest path between two vertices. You can prove that the path

between the root and any node in the BFS tree is the shortest path between the

root and the node

4. Finding all connected components. A connected component is a maximal

connected subgraph in which every pair of vertices are connected by a path.

5. Detecting /Finding whether there is a cycle in the graph.

6. Testing whether a graph is bipartite. A graph is bipartite if the vertices of the

graph can be divided into two disjoint sets such that no edges exist between

vertices in the same set.

Programming Excersice

30

Represent the following graph. Traverse using DFS and BFS

BFS & DFS Programming Exercise

31

public static void main(String[] args) { Graph<String> graph = new Graph<String>(); graph.addVertice("V0"); graph.addVertice("V1"); graph.addVertice("V2"); graph.addVertice("V3"); graph.addVertice("V4"); graph.addVertice("V5"); graph.addEdge(0,1); graph.addEdge(1,2); graph.addEdge(1,3); graph.addEdge(1,4); graph.addEdge(4,5); graph.addEdge(2,5); graph.addEdge(3,5); graph.showData(); System.out.println("\nDFS >>> "); graph.clearVisitedMarkers(); graph.dfs(0); System.out.println("\nBFS >>> "); graph.clearVisitedMarkers(); graph.bfs(0);

}

BFS & DFS Programming Exercise

32

public class Graph <E> { private ArrayList<E> vertices; private ArrayList< ArrayList<Integer> > neighbors; private ArrayList<Boolean> visitedMarkers; public Graph() { vertices = new ArrayList<E>(); neighbors = new ArrayList < ArrayList<Integer> >(); visitedMarkers = new ArrayList<Boolean>(); } public void addVertice(E newVertice){ vertices.add(newVertice); visitedMarkers.add(false); neighbors.add(new ArrayList<Integer>() ); } public void addEdge( int v1, int v2){ ArrayList<Integer> adjacent1 = neighbors.get(v1); if (!adjacent1.contains(v2)) neighbors.get(v1).add(v2); ArrayList<Integer> adjacent2 = neighbors.get(v2); if (!adjacent2.contains(v1)) neighbors.get(v2).add(v1); }

BFS & DFS Programming Exercise

33

public void markVerticeAsVisited(int v){ visitedMarkers.set(v, true); } public void clearVisitedMarkers(){ for(int i=0; i<vertices.size(); i++){ visitedMarkers.set(i, false); } } public void showData() { for (int i=0; i<vertices.size(); i++){ System.out.printf("\nVertice[%d]= %s", i, vertices.get(i)); } for (int i=0; i < vertices.size(); i++){ System.out.printf("\nneighbors[%d]: ", i); ArrayList<Integer> adjacent = neighbors.get(i); for (int j=0; j<adjacent.size(); j++){ System.out.printf(" %d,", adjacent.get(j) ); } } }//showData

34

public void dfs(int v) { visitedMarkers.set(v, true); for(int n : neighbors.get(v)){ if (!visitedMarkers.get(n)){ System.out.printf("[v%d-v%d] ", v, n); dfs(n); } } }//dfs

BFS & DFS Programming Exercise

BFS & DFS Programming Excersice

35

public void bfs(int v){ ArrayList<Integer> queue = new ArrayList<Integer>(); clearVisitedMarkers(); visitedMarkers.set(v, true); System.out.printf("BFS >>> starting at: v%d \n", v); queue.add(v); while(queue.size() > 0){ int currentDequeuedVertice = queue.remove(0); ArrayList<Integer> adjacents = neighbors.get(currentDequeuedVertice); for(int i=0; i<adjacents.size(); i++){ int adjacentNode = adjacents.get(i); if (!visitedMarkers.get(adjacentNode)){ System.out.printf("[v%d-v%d] ", currentDequeuedVertice, adjacentNode); queue.add(adjacentNode); visitedMarkers.set(adjacentNode, true); }//if }//for }//while }//bfs }

Case: The Nine Tail Problem

36

1. Nine coins are placed in a three by three matrix with some face up and some face down.

2. A legal move is to take any coin that is face up and reverse it, together with the coins adjacent to it (this does not include coins that are diagonally adjacent).

3. Your task is to find the minimum number of the moves that lead to all coins face down.

H

T

T

T

H

H

H

H

H

H

T

H

T

H

H

T

T

T

T

T

T

T

T

T

T

T

T

H

T

T

T

H

H

H

H

H

Case: The Nine Tail Problem

37

H

T

H

T

H

H

T

T

T

T

T

T

T

T

T

T

T

T

Finding Eulerian Paths

38

An Eulerian path traverses each edge of a connected graph G exactly once.

It exists only if there are no more than two odd nodes.

1. Pick an odd vertex to start.

2. From that vertex move to a node using an “unvisited” edge.

3. Mark that edge as “visited” (see note)

4. Try to repeat 2-4 until all edges have been traversed

Note: DFS algorithm marks nodes as visited.

1

2 4

3

2

2

3

3

1

2 4

3

2

3

3

3

2

1

More than two odd nodes ⟶ no Euler Path

The Hamiltonian Path Problem

39

Def. A Hamiltonian path in a graph is a path that visits each vertex in the graph exactly once.

Def. A Hamiltonian cycle is a cycle that visits each vertex in the graph exactly once and returns to the starting vertex.

Notes:

Problem is NP-Complete

Many applications such as: Scheduling the Traveling Salesman Itinerary.