HDU 1233 还是畅通工程

题解:kruskal算法模板

krcukal算法:

对边进行排序,从最小的开始加入集合,每次都检查是不是构成了环,如果有环,说明这条边是多余的,因为这条边所能实现的联通的功能,已经被前面更短的边实现了。

#include<iostream>
#include<algorithm>
using namespace std;
const int maxn=10005;
struct node { int from,to,len;} edge[maxn];
int n,fa[maxn],m,ans,q;
bool cmp(node a,node b) { return a.len<b.len; }
int Find(int x)
{
    if(fa[x]==x) return x;
    return fa[x]=Find(fa[x]);
}
void Merge(int x,int y)
{
    x=Find(x),y=Find(y);
    if(x!=y) fa[y]=x;
}
int kruskal()
{
    sort(edge,edge+m,cmp);
    for(int i=0;i<=n;i++) fa[i]=i;//初始化并查集
    ans=0;
    for(int i=0;i<m;i++)//一条边的两个端点不在同一个集合,则选它,并合并端点
        if(Find(edge[i].from)!=Find(edge[i].to)) Merge(edge[i].from,edge[i].to),ans+=edge[i].len;
    return ans;
}
int main()
{
    while(cin>>n,n)
    {
        m=n*(n-1)/2;
        for(int i=0;i<m;i++) cin>>edge[i].from>>edge[i].to>>edge[i].len;
        cout<<kruskal()<<endl;
    }
    return 0;
}

猜你喜欢

转载自blog.csdn.net/nwpu2017300135/article/details/80551979
今日推荐