标签:
一个篮球队有n个篮球队员,每个队员都有联系方式(如电话、电子邮件等)。但并不是每个队员的联系方式都公开,每个队员的联系方式只有一部分队员知道。问队员可以分成多少个小组,小组成员之间可以相互通知(包括一个队员一个组,表示自己通知自己)。
输入文件有若干行
第一行,一个整数n,表示共有n个队员(2<=n<=100)
下面有若干行,每行2个数a、b,a、b是队员编号,表示a知道b的通讯方式。
输出文件有若干行
第一行,1个整数m,表示可以分m个小组,下面有m行,每行有若干个整数,表示该小组成员编号,输出顺序按编号由小到大。
8
1 2 3
4 6
5
7 8
9
10
11
12
tarjan求有多少了连通块,并按顺序输出
输出 先给每个块中元素排序,在对每个块排序(按照头元素大小)
#include <cstdio> #include <iostream> #include<algorithm> #define N 200 using namespace std; struct edge { int to,next; }e[N*N]; struct node { int c[N],size; }p[N]; int dfn[N],Low[N],sz[N]; int index,Count; bool instack[N]; int s[N],top; int head [N]; int cnt; void ins(int u,int v) { e[++cnt].to = v; e[cnt].next = head[u]; head[u] = cnt; } void tarjan(int k){ dfn[k]=Low[k]=++index; instack[k]=true; s[++top]=k; for (int i=head[k];i;i=e[i].next) { int j=e[i].to; if(dfn[j]==0){ tarjan(j); Low[k]=min(Low[k],Low[j]); }else if(instack[j]) Low[k]=min(Low[k],dfn[j]); } if(dfn[k]==Low[k]) { int j; Count++; do{ j=s[top--]; instack[j]=false; p[Count].size++; sz[p[Count].size] = j; }while(j!=k); sort(sz+1,sz+p[Count].size+1); for (int i=1;i<=p[Count].size;i++) p[Count].c[i] = sz[i]; } } int cmp(const node &a,const node &b) { return a.c[1] < b.c[1]; } int cmp2(const int &a,const int &b) { return a<b; } int main(){ int m,u,v,n=0; freopen("jdltt.in","r",stdin); freopen("jdltt.out","w",stdout); scanf("%d",&n); while (scanf("%d%d",&u,&v)==2) ins(u,v); for(int i=1;i<=n;i++) if(dfn[i]==0) tarjan(i); sort(p+1,p+1+Count,cmp); printf("%d\n",Count); for(int i=1;i<=Count;i++) { for (int j=1;j<=p[i].size;j++) printf("%d ",p[i].c[j]); printf("\n"); } return 0; }
标签:
原文地址:http://www.cnblogs.com/liumengyue/p/5494801.html