hdu_1233(最小生成树)
生活随笔
收集整理的這篇文章主要介紹了
hdu_1233(最小生成树)
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
http://acm.hdu.edu.cn/showproblem.php?pid=1233 ?這道題是昨天那道暢通工程的升級題,用了最小生成樹的思想,我是參考白書上的kruskal 代碼做了這道題(PS:白書果然 是王道!)。首先并查集是必不可少的,將兩點之間的連 線看成邊,這次不僅要將并查集初始化,還要初始化邊的序號,用數組r來存儲邊的序號, 題目要求有m=n*(n-1)/2條路。我們用u[i],v[i],w[i],分別表示兩個端點的序號,以及 兩點間的距離,然后根據w[i]給邊間接排序(排序的對象是邊的序號,而不是邊的長度)。 下一步就是在所有集合由距離的小到 大連接起來。 ?下面是代碼: #include<stdio.h>
#include<stdlib.h>
#define SIZE 10010
int p[105],u[SIZE],v[SIZE],w[SIZE],r[SIZE];
int n,m;
int find(int x)
{
return p[x] == x ? x : (p[x] =find(p[x]) );
}
int cmp(const void *_p,const void *_q) /* 間接排序函數*/
{
int *p=(int *)_p;
int *q=(int *)_q;
return w[*p]-w[*q];
}
int main()
{
int i,e,x,y,j,ans;
while(scanf("%d",&n) , n)
{
ans = 0;
m = n*(n-1)/2;
for(j = 0; j < m; j ++) /*輸入村莊序號以及兩者之間的距離*/
{
scanf("%d%d%d",&u[j],&v[j],&w[j]);
u[j]--;
v[j]--;
}
for( i = 0; i < n; i ++) p[i] = i; //初始化并查集
for( i = 0; i < m; i ++) r[i] = i; //初始化邊序號
qsort(r,m,sizeof(r[0]),cmp); //給邊排序
for( i = 0; i < m; i ++)
{
e = r[i]; x = find(u[e]); y = find(v[e]); //找出兩個村莊所在集合編號
/*不在一個集合,但現在有連接則合并*/
if( x != y) {
ans += w[e]; //每當合并將二者之間的距離加上。
p[x] = y;
}
}
printf("%d\n",ans);
}
return 0;
}
當然可能有些樣例i不用循環到m就已經將所有的集合連接起來了,但是到m也沒關系,時間復雜度 并不高!我自己先把這個方法消化一下...?????
????????
????
????????
????
???
#include<stdlib.h>
#define SIZE 10010
int p[105],u[SIZE],v[SIZE],w[SIZE],r[SIZE];
int n,m;
int find(int x)
{
return p[x] == x ? x : (p[x] =find(p[x]) );
}
int cmp(const void *_p,const void *_q) /* 間接排序函數*/
{
int *p=(int *)_p;
int *q=(int *)_q;
return w[*p]-w[*q];
}
int main()
{
int i,e,x,y,j,ans;
while(scanf("%d",&n) , n)
{
ans = 0;
m = n*(n-1)/2;
for(j = 0; j < m; j ++) /*輸入村莊序號以及兩者之間的距離*/
{
scanf("%d%d%d",&u[j],&v[j],&w[j]);
u[j]--;
v[j]--;
}
for( i = 0; i < n; i ++) p[i] = i; //初始化并查集
for( i = 0; i < m; i ++) r[i] = i; //初始化邊序號
qsort(r,m,sizeof(r[0]),cmp); //給邊排序
for( i = 0; i < m; i ++)
{
e = r[i]; x = find(u[e]); y = find(v[e]); //找出兩個村莊所在集合編號
/*不在一個集合,但現在有連接則合并*/
if( x != y) {
ans += w[e]; //每當合并將二者之間的距離加上。
p[x] = y;
}
}
printf("%d\n",ans);
}
return 0;
}
當然可能有些樣例i不用循環到m就已經將所有的集合連接起來了,但是到m也沒關系,時間復雜度 并不高!我自己先把這個方法消化一下...?????
????????
????
????????
????
???
轉載于:https://www.cnblogs.com/Yu2012/archive/2011/09/26/2190708.html
總結
以上是生活随笔為你收集整理的hdu_1233(最小生成树)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 近似与精确——《狂人C》习题解答15(第
- 下一篇: 极有收藏价值的一组难求纯4位数字.com