hdu 1233(最小生成树问题) 克鲁斯卡尔算法

来源:互联网 发布:网络打鸡血是什么意思 编辑:程序博客网 时间:2024/05/18 03:21
#include <stdio.h>#include <iostream>#include <algorithm>using namespace std;struct node{    int a,b,len;}G[5055];int cmp(const node &a,const node &b){    return a.len<b.len;}int father[120];void makeSet(){    for(int i=1; i<=110; i++)    {        father[i] = i;    }}int Find(int x) //迭代版本{    int tempRoot;    int root = x;    while(root != father[root]) //找到根节点。        root = father[root];    while(x != root)    {        tempRoot = father[x]; //x的父节点用临时变量存一下。        father[x] = root; //x的父节点设置成根 (x 压缩到根节点了)        x = tempRoot;   //x 赋值为 x的父节点(之前存过的);    }    return root; // 最后返回根节点}void Union(int x,int y){    int xroot ,yroot;    xroot = Find(x);    yroot = Find(y);    if(xroot == yroot ) return;    else        father[xroot] = yroot; } int len;     int n; int ans=0;void kruscal()   //克鲁斯卡尔算法 : 先让权排序,然后寻找每个数的{                 //根,如果不同一个祖先,权相加。    ans = 0;    for(int i = 0; i < len; i++ )    {        if(Find(G[i].a) != Find(G[i].b))        {            Union(G[i].a,G[i].b);            ans += G[i].len;        }    }}int main(){    while(scanf("%d",&n)!=EOF && n)    {         len = n* (n - 1) / 2;        for(int i = 0 ; i < len ; i++)        {            scanf("%d%d%d",&G[i].a,&G[i].b,&G[i].len);        }         makeSet();         sort(G,G+len,cmp);         kruscal();         printf("%d\n",ans);    }    return 0;}
0 0
原创粉丝点击