//我写的没有用典型的并查集做,利用bfs选择出受感染的小组,然后再统计这些小组里共有多少人 #include<stdio.h> #include<string.h> #include<queue> using namespace std; int num[500][30005]; int ans,n,m; int main() { while(scanf("%d%d",&n,&m)==2&&(m+n)) { if(!m) printf("1/n"); else { int i,j; ans=0; queue<int> q; for(i=0;i<m;i++) { scanf("%d",&num[i][0]); int k=num[i][0]; for(j=1;j<=k;j++) { scanf("%d",&num[i][j]); if(!num[i][j]) { num[i][0]*=-1; q.push(i); } } } if(q.empty()) { printf("1/n"); continue; } while(!q.empty()) { int t=q.front(); q.pop(); for(i=0;i<m;i++) { if(num[i][0]>0) { for(j=1;j<=-1*num[t][0];j++) { for(int k=1;k<=num[i][0]&&num[i][0]>0;k++) { if(num[t][j]==num[i][k]) { num[i][0]*=-1; q.push(i); break; } } if(num[i][0]<0)break; } } } } bool temp[30005]; memset(temp,0,sizeof(temp)); for(i=0;i<m;i++) { if(num[i][0]<0) { for(j=1;j<=-1*num[i][0];j++) if(!temp[num[i][j]]) { ans++; temp[num[i][j]]=1; } } } printf("%d/n",ans); } } return 0; } //以下是别人写的并查集,附在这里学习一下 #include <iostream> #include <algorithm> #include <cmath> #include <string> #include <set> #include <queue> #include <map> using namespace std; struct susp { int father; int rank; }susp[30010]; int find(int i) { int j=i; while(1) { if(susp[j].father<0) { if(i!=j) { susp[i].father=j; } return j; } j=susp[j].father; } } int main() { //freopen("test.txt","r",stdin); int n,m; int k,a,b; int x,y; int i; while(scanf("%d%d",&n,&m)&&(n!=0||m!=0)) { for(i=0;i<n;i++) { susp[i].father=-1; susp[i].rank=1; } while(m--) { scanf("%d",&k); if(k>0) { scanf("%d",&a); x=find(a); for(i=1;i<k;i++) { scanf("%d",&b); y=find(b); if(x!=y) { susp[y].father=x; susp[x].rank+=susp[y].rank; } } } } printf("%d/n",susp[find(0)].rank); } return 0; }