Introduction to graphs
Started with Koenigsberg bridge problem (search the web for it...), and the following problem: In the figure below, it is possible to trace a path with a pencil so that the pencil never leaves the paper, and each line segment in the drawing is crossed exactly once: ===>
Is this possible in this next figure? figure 1: Consider the following diagrams: figure 2: figure 3: The figure above is a drawing of a graph. The letters represent nodes (also called vertices) of the graph. The lines connecting pairs of letters represent edges.
Graph terminology: * A graph G = (V,E) is specified by a set of vertices V and a set of edges E. Each edge is specified by a pair of vertices (u,v). * The neighbors of a vertex v are the vertices w such that (v,w) is an edge (i.e., (v,w)∈ E. * a path is a sequence of vertices where each consecutive pair is connected by an edge.\ The path is simple if no vertex is repeated on the path. * The length of the path is the number of edges on it. * The distance between two nodes is the length of the shortest path between them. * a cycle is a path whose start vertex and end vertex are the same.\ The cycle is simple if the start vertex occurs twice and each other vertex occurs at most once on the path. * A pair of vertices is connected if there exists a path starting at one and ending at the other. \ In this case we also say that each vertex in the pair is reachable from the other. * a connected component of the graph is a collection of vertices reachable from some vertex. * the graph itself is connected if it has only one connected component (all vertices are reachable from each other). * the degree of a vertex is the number of edges the vertex is in.
The question about figure 1 is equivalent to the following question: : Does the graph in figure 3 have a path that uses each edge exactly once?
Depth-first search (DFS)
Depth-first search is a "backtracking" method of exploring a graph. It searches from vertex to vertex, backtracking when it encounters vertices that have already been discovered. Here is pseudo-code: DFS(graph G, vertex v) Array<int> visited(0); DFS1(G, v, visited); end DFS1(graph G, vertex v, Array<int>& visited) if (visited[v] == 1) return visited[v] = 1 for each neighbor w of v do DFS1(G, w, visited) end
We demonstrated DFS on an example. DFS on classifies the edge into two kinds: * DFS tree edges -- these are the edges (v,w) such that DFS1(G, w, visited) is \ called directly from within DFS1(G, v, visited) when w is not yet visited. * back edges -- these are the other edges. The tree edges form a tree (essentially a recursion tree for the DFS). For any back edge (u,v), either u is a descendant of v in the tree or vice versa. In a graph with N vertices and M edges, the running time for DFS is O(N+M), because the work done for each vertex is proportional to the degree of the vertex, and the sum of the vertex degrees is 2M.
Breadth-first search
DFS is called "depth first" because it descends into the graph as quickly as possible. Breadth-search first, in contrast, explores nodes by following a "wave front". It explores in order of their distance from the start vertex. BFS(graph G, vertex v) FIFO_Queue Q; Array<int> distance(-1); distance[v] = 0; insert vertex v into the queue Q. while (Q is not empty) take the next vertex W off the front of the queue Q for each neighbor X of W do if (distance[X] == -1) then distance[X] = distance[W] + 1 add vertex X to the tail of the queue Q end
We demonstrated BFS on an example, and noted that it ran in time O(N+M) on any graph with N vertices and M edges.
|