Description
We will use the following (standard) Definitions from graph theory. Let
VBe a nonempty and Finite Set, its elements being called vertices (or nodes). Let
EBe a subset of the Cartesian Product
V × V, Its elements being called edges. Then
G = (V, E)Is called a directed graph.
Let
NBe a positive integer, And let
P = (E1,..., en)Be a sequence of Length
NOf Edges
Ei, ESuch that
Ei = (Vi, vi + 1)For a sequence of vertices
(V1,..., vn + 1). Then
PIs called a path from vertex
V1To Vertex
Vn + 1In
GAnd we say that
Vn + 1Is reachable from
V1, Writing
(V1 → VN + 1).
Here are some new definitions. A node
VIn a graph
G = (V, E)Is called a sink, if for every node
WIn
GThat is reachable from
V,
VIs also reachable from
W. The bottom of a graph is the subset of all nodes that are sinks, I. e .,
Bottom (G) = {v ε v |? Wε v :( v → W )? (W → v )}. You have to calculate the bottom of certain graphs.
Input
The input contains several test cases, each of which corresponds to a Directed Graph
G. Each test case starts with an integer number
V, Denoting the number of vertices
G = (V, E), Where the vertices will be identified by the integer numbers in the set
V = {1,..., V}. You may assume that
1 <= V <= 5000. That is followed by a non-negative integer
EAnd, thereafter,
EPairs of vertex identifiers
V1, W1,..., VE, weWith the meaning that
(Vi, WI) ε E. There are no edges other than specified by these pairs. The last test case is followed by a zero.
Output
For each test case output the bottom of the specified graph on a single line. to this end, print the numbers of all nodes that are sinks in sorted order separated by a single space character. if the bottom is empty, print an empty line.
Sample Input
3 31 3 2 3 3 12 11 20
Sample output
1 32
The essence of the question is to find strongly connected subgraph with no degree of output, and sink with no degree of output, the bottom of graph.
It is to use the Tarjan algorithm to find a strongly connected subgraph, and use the identification number to identify each strongly connected subgraph, and then record which strongly connected subgraph each vertex belongs.
The program carries detailed Annotations:
# Include <stdio. h> # include <stdlib. h >#include <vector >#include <algorithm> # include <stack> using namespace STD; const int max_v = 5001; vector <int> graadj [max_v]; // int conno, vtocon [max_v]; // an array int low [max_v] indicating the number of strongly connected subgraphs and the number of strongly connected subgraphs corresponding to the vertex. // minimum ID. If all vertices belonging to this ID belong to the same connected subgraph int STK [max_v], top; // array indicates stack bool vis [max_v]; // records whether the accessed vertex int out [max_v]; // The degree of output of the strongly connected subgraph. If the degree of output is zero, change the strongly connected subgraph to sinktemplate <typename T> inline bool. Equ (T T1, t T2) {return T1 = t2;} void dfstar (int u, int NO = 1) {LOW [u] = no; // each time a vertex is recursively entered, the initial representation is low [] STK [++ top] = u; // each vertex is recorded into the stack vis [u] = true; // indicates whether int n = (INT) graadj [u] has been accessed. size (); For (INT I = 0; I <n; I ++) {int v = graadj [u] [I]; If (! Vis [v]) {dfstar (V, no + 1); // recursive here if (low [u]> low [v]) low [u] = low [v]; // update the minimum ID} else if (! Vtocon [v] & low [u]> low [v]) low [u] = low [v]; // update} If (equ (low [u], no) // if the minimum identification number is the same as the initial number of the recursion, a subgraph is located. {++ conno; int V; do {v = STK [top --]; // output stack vtocon [v] = conno; // The vertex corresponds to the subgraph number} while (V! = U); // After the stack is output to the current vertex, all the vertices of the sub-graph are output to the stack.} void Tarjan (int n) {conno = 0; // remember to clear the previous work fill (vtocon, vtocon + n + 1, 0); fill (low, low + n + 1, 0); fill (VIS, vis + n + 1, false); Top =-1; for (INT u = 1; U <= N; U ++) if (! Vis [u]) dfstar (U);} int main () {int V, E, U, V; while (~ Scanf ("% d", & V, & E) & V) {for (INT I = 1; I <= V; I ++) {graadj [I]. clear (); // clear} For (INT I = 0; I <E; I ++) {scanf ("% d", & U, & V ); graadj [u]. push_back (V); // create an adjacent table represented by vector} Tarjan (V); fill (Out, Out + conno + 1, 0); For (INT u = 1; U <= V; U ++) {int n = graadj [u]. size (); For (INT I = 0; I <n; I ++) {int v = graadj [u] [I]; If (vtocon [u]! = Vtocon [v]) {out [vtocon [u] ++; // records the degree of output of Strongly Connected subgraph numbers }}for (INT u = 1; U <= V; U ++) // The output is zero, that is, the answer: Graph bottom {If (! Out [vtocon [u]) printf ("% d", U);} putchar ('\ n');} return 0 ;}
Poj 2553 the bottom of graph strongly connected graph question