b_lg_刻录光盘(floyd传递闭包+并查集)

有N个营员(2<=N<=200),每个营员的编号为1~N。LHC给每个人发了一张调查表,
让每个营员填上自己愿意让哪些人到他那儿拷贝资料。
当然,如果A愿意把资料拷贝给B,而B又愿意把资料拷贝给C,则一旦A获得了资料,则B,C都会获得资料。
现在,请你编写一个程序,根据回收上来的调查表,
帮助LHC计算出组委会至少要刻录多少张光盘,才能保证所有营员回去后都能得到夏令营资料?

...

#include<bits/stdc++.h>
using namespace std;
const int N=205;
int n,fa[N],f[N][N];
int find(int u) {
    return fa[u]==u ? u : fa[u]=find(fa[u]);
}
int main() {
    std::ios::sync_with_stdio(false); cin.tie(0); cout.tie(0);
    cin>>n; for (int i=1,x; i<=n; i++) while (cin>>x, x) f[i][x]=1;

    for (int k=1; k<=n; k++)
    for (int i=1; i<=n; i++)
    for (int j=1; j<=n; j++) if (f[i][k] && f[k][j])
        f[i][j]=1;
    for (int i=1; i<=n; i++) fa[i]=i;
    for (int i=1; i<=n; i++)
    for (int j=1; j<=n; j++) if (f[i][j]) {
        fa[j]=find(i);
    }
    int ans=0;
    for (int i=1; i<=n; i++) if (fa[i]==i)
        ans++;
    cout<<ans;
    return 0;
}
原文地址:https://www.cnblogs.com/wdt1/p/13807749.html