Lecture 27:  Graphs

Announcements/Reminders

·       homework #8 due today

·       make sure your programs compile & run on the instructional Unix machines

·       lunch on Monday for C.S. majors – you're welcome to come, meet c.s. majors, ask them questions

 

graphs:  generalization of trees

·       both have nodes and edges

·       in a tree, the root has no incoming edges

other nodes have exactly one incoming edge

·       in a graph, there are no restrictions

 

two types of graphs:

                directed                                  undirected

 

                                                    

 

 

 

 


either type of graph can be connected or not connected

we will consider mainly directed graphs

can have labels

·       associated with the nodes

·       associated with the edges

 

example:  airline routes with flight times

        (nodes are the cities, edges contain flight times)

 

0.5 hr

 

1.5 hrs

 

Madison

 
              

 

Terminology:

·       predecessor/successor

·       paths:   Madison ®  Green Bay ® Chicago  (like in trees)

acyclic path:  no node is repeated

cyclic path:  node is repeated

·       DAG:  directed, acyclic graph (no cyclic paths)

Graphs Can Represent Useful Information

·       nodes represent objects (in the real world)

    & edges represent relationships

e.g.,  airline routes:  nodes = cities &  edges = flights

labels on the edges = time, distance, price, …

 

simple relationship: 

edges represent precedence between nodes that are tasks

        e.g., c.s. courses with prerequisites

                   

 

CFG:  control flow graph

nodes = statements & conditions

edges = flow of control

example

Boolean lookup(List L) {

  Boolean flag;

  int k = 0;

  while ( k < L.size() ) {

    if (…) flag = true;

    k++;

  }

  return flag;

}        

standard graph operations can answer questions like

·       can I fly non-stop from Chicago to Green Bay?

·       what is the minimum number of hops from A to B?

·       how many C.S. classes must I take before I take cs536?

·       can variable flag be returned without being initialized?

 

Representing Graphs

·       one class for the graph:  Graph

·       one class for the individual nodes:  Graphnode

Graphnode object has fields for

o      data

o      successors  (e.g., an array, List, Set)   

- contains refs to Graphnodes

o      predecessors   [sometimes useful]

Graph object has fields for

o      nodes  (e.g., array, List, Set, …)

or pointer to root if there is a root – e.g., in CFG

o      size (?)

Example

Name

 

successors

 

 

 

Madison

 

Name

 

successors

 

 

 

Chicago

 

Name

 

successors

 

 

 

nodes

 

size

 

4

 
              

 G

 
 

etc.

 

“Green

    Bay”

 
           

Graph Operations

two orderly ways to traverse nodes/edges:

o      depth-first traversal

o      breadth-first traversal

Depth-first traversal can answer the following questions:

        (song)

·       is the graph connected? – follow predecessors & successors

·       does the graph have a cycle?

·       is there a path from node j to node k?

·       what are all the nodes reachable from j?

·       for an acyclic graph, what is a topological ordering              i.e., and ordering such that for every node n,             n comes before all successors                                      – e.g., a legal ordering to take c.s. courses

NOT:  what is the shortest path from one node to another

Depth-first traversal:  implementation

idea

·       start at a given node n

·       follow an edge out of n (to m)

·       follow an edge out of m

·       etc – getting as far from n as possible before following other edges out of n

algorithm

        dft(n)

·       mark n "visited"

·       for each of n's successors m,

o      if m is "unvisited", dft(m)

example

            A              B                               dft(A)

                                                            

X

 

dft(C)

 
            C              D                              

dft(E)

 

dft(D)

 
                                               

X

 

X

 

dft(F)

 

dft(B)

 
            E              F                  

                                                 

order in which nodes are visited:   A  C  D  B  F  E

another possibility:                        A  C  F  E  D  B

You try: do dft from C

 

Implementation

·       visited/unvisited "marks" can be implemented using a Boolean field in each node (initialized to false)

·       actual code:

   static void dft( Graphnode n) {

1    n.visited = true;

2    Iterator it = n.getSuccessors().iterator();

3    while(it.hasNext()) {

4      Graphnode m = (Graphnode) it.next();

5      if (!m.visited) dft(m);

     }

   }

Time for Depth-first Traversal

·       one recursive call for each node reachable from n

·       each call goes through entire sucessors list of the current node

so, the total time is 

        T(n) = (c1 + e1 ´ c2) + (c1 + e2 ´ c2) ++  (c1 + er ´ c2)

 c1 = time for statements 1 and 2;

 c2 = time for statements 3, 4 and 5;

 ei = number of successor edges for ith node visited

 r = number of nodes reachable from n)

   which is proportional to:

        the number of nodes, r,  that are reachable from n

    ´ the avg. number of outgoing edges from each node

worst case:  r = N

        T(n) = N ´ c1 + c2 ´ (e1 + e2 + ... + eN) = N ´ c1 + E ´ c2

               = O(N + E) 

where N = # of nodes, E = # of edges in the graph

or:  T(n) = N ´ (c1 + c2 ´ E/N) = O(N + E)