Online Judge | Problem Set | Authors | Online Contests | User | ||||||
---|---|---|---|---|---|---|---|---|---|---|
Web Board Home Page F.A.Qs Statistical Charts | Current Contest Past Contests Scheduled Contests Award Contest |
Kruskal模板算法,贴代码,飘过~#include <iostream> #include <algorithm> #define MAX 55 using namespace std; int father[MAX]; //记录各节点的父节点 int m[MAX][MAX]; //存储采用所用线缆后的图的邻接表 int cmax; struct edge { int x,y; int w; }e[MAX * MAX / 2]; //用来存储各个边的信息,x点至y点的权值为w int find_set(int a) //查找a所在的集合,回溯时顺便压缩路径 { if(a != father[a]) { father[a] = find_set(father[a]); } return father[a]; } void Union(int x,int y,int w) //合并x和y所在的集合,并用cmax记录所有边的权值之和 { if(x == y) return; father[y] = x; cmax += w; } bool cmp(edge a,edge b) //非降序排序排序函数 { return a.w < b.w; } int main() { int n,r,i,j,s,t,tmp,k; while(scanf("%d%d",&n,&r) != EOF && n!= 0) { k = 0; cmax = 0; memset(m,-1,sizeof(m)); //初始化数组 if(r == 0) //如果r == 0,直接下次循环 { cout << 0 << endl; continue; } for(i = 0;i < r;i++) { cin >> s >> t >> tmp; //输入线缆的数据,连接s和t权值为tmp的线缆 if(s > t) //只对m的上三角信息进行存储 { int temp = s; s = t; t = temp; } if(m[s-1][t-1] == -1 || m[s-1][t-1] > tmp) m[s-1][t-1] = tmp; //只保留连接两点的线缆长度最短的边 } //Kruskal算法 for(i = 0;i < n;i++) { father[i] = i; for(j = 0;j < n;j++) { if(i < j ) if(m[i][j] != -1) { e[k].x = i; e[k].y = j; e[k].w = m[i][j]; k++; } } } sort(e,e + k,cmp); for(i = 0;i < k;i++) { Union(find_set(e[i].x),find_set(e[i].y),e[i].w); } cout << cmax << endl; } return 0; } Followed by: Post your reply here: |
All Rights Reserved 2003-2013 Ying Fuchen,Xu Pengcheng,Xie Di
Any problem, Please Contact Administrator