Link: http://poj.org/problem?id=2553
求缩点后出度为0的点。。。 tarjan again。。。
首次用了memcpy方法 感觉不错!
注意init()要在输入了 m n之后调用,一般来说上轮case里数组是 a[i] ++形式的 要再次赋初值
而有变量cnt控制数组大小的数组 不必赋值 只要控制cnt=0 就可以了
如for(int i=1; i<=cnt; i++) a[i]=xxxx; 这类


#include <cstdio> #include <iostream> #include <stack> #include <algorithm> using std::stack; using std::sort; const int maxn = 5005, INF = (1<<30); bool vis[maxn], inStack[maxn]; int dfn[maxn], low[maxn], belong[maxn], size[maxn], m, n, round, cnt; int out[maxn], arr[maxn][maxn]; int ans[maxn]; struct node { int index; node *next; }edge[maxn]; stack<int> s; int min(int a, int b) { return a<=b ?a :b ; } void tarjan(int u) { int i; dfn[u] = low[u] = round ++ ; vis[u] = 1; inStack[u] = 1; s.push(u); node *p = edge[u].next; while( p != NULL ) { int v = p->index; if( !vis[v] ) { tarjan(v); low[u] = min(low[u], low[v]); } else if( inStack[v] ) low[u] = min(low[u], dfn[v]); p = p->next; } if( low[u] == dfn[u] ) { cnt ++; while(i = s.top()) { size[cnt] ++; arr[cnt][size[cnt]] = i; belong[i] = cnt; inStack[i] = 0; s.pop(); if( i==u ) break; } } } void init() { cnt = 0; memset(ans, 0, sizeof(ans)); memset(vis, 0, sizeof(vis)); memset(out, 0, sizeof(out)); memset(size, 0, sizeof(size)); memset(inStack, 0, sizeof(inStack)); for(int i=1; i<=n; i++) { edge[i].index = i; edge[i].next = NULL; } } int check() { for(int i=1; i<=n; i++) if( !vis[i] ) return i; return 0; } int main() { int i, a, b; while(scanf("%d", &n), n!=0) { scanf("%d", &m); init(); for(i=1; i<=m; i++) { scanf("%d %d", &a, &b); if( a == b ) continue; node *p = (node *)malloc(sizeof(node)); p->index = b; p->next = edge[a].next; edge[a].next = p; } while( i=check() ) tarjan(i); for(i=1; i<=n; i++) { node *p = edge[i].next; while( p != NULL ) { if( belong[i] != belong[p->index]) out[belong[i]]++ ; p = p->next; } } int minNum = INF, ansCnt = 0; for(i=1; i<=cnt; i++) { if(out[i] == 0) { memcpy(ans+ansCnt, arr[i]+1, sizeof(int)*size[i]); ansCnt += size[i]; } } sort( ans, ans+ansCnt ); for(i=0; i<ansCnt-1; i++) printf("%d ", ans[i]); printf("%d\n", ans[i]); } return 0; }