#NEWLINE# def checkJobGraphAcylic( self ) : #NEWLINE# #INDENT# '\n        :raises toil.job.JobGraphDeadlockException: if the connected component         of jobs containing this job contains any cycles of child/followOn dependencies         in the *augmented job graph* (see below). Such cycles are not allowed         in valid job graphs. \n        \n        A follow-on edge (A, B) between two jobs A and B is equivalent         to adding a child edge to B from (1) A, (2) from each child of A,         and (3) from the successors of each child of A. We call each such edge         an edge an "implied" edge. The augmented job graph is a job graph including         all the implied edges.\n\n        For a job graph G = (V, E) the algorithm is ``O(|V|^2)``. It is ``O(|V| + |E|)`` for         a graph with no follow-ons. The former follow-on case could be improved!\n        ' #NEWLINE# roots = self . getRootJobs ( ) #NEWLINE# if ( len ( roots ) == 0 ) : #NEWLINE# #INDENT# raise JobGraphDeadlockException ( 'Graph contains no root jobs due to cycles' ) #NEWLINE# #UNINDENT# extraEdges = self . _getImpliedEdges ( roots ) #NEWLINE# visited = set ( ) #NEWLINE# for root in roots : #NEWLINE# #INDENT# root . _checkJobGraphAcylicDFS ( [ ] , visited , extraEdges )