题目描述 Description
学校需要将n台计算机连接起来,不同的2台计算机之间的连接费用可能是不同的。为了节省费用,我们考虑采用间接数据传输结束,就是一台计算机可以间接地通过其他计算机实现和另外一台计算机连接。
为了使得任意两台计算机之间都是连通的(不管是直接还是间接的),需要在若干台计算机之间用网线直接连接,现在想使得总的连接费用最省,让你编程计算这个最小的费用。
输入描述 Input Description
输入第一行为两个整数n,m(2<=n<=100000,2<=m<=100000),表示计算机总数,和可以互相建立连接的连接个数。接下来m行,每行三个整数a,b,c 表示在机器a和机器b之间建立连接的话费是c。(题目保证一定存在可行的连通方案, 数据中可能存在权值不一样的重边,但是保证没有自环)
输出描述 Output Description
输出只有一行一个整数,表示最省的总连接费用。
样例输入 Sample Input
3 3
1 2 1
1 3 2
2 3 1
样例输出 Sample Output
2
数据范围及提示 Data Size & Hint
最终答案需要用long long类型来保存
Kruskal + 并查集
在find()函数中,一直记成 return f[x]==x?x:find(f[x]);
结果就一直超时,各种纠结。。
跟别人的代码对比也没找出来,最后终于发现是这个地方出了问题 应改为 return f[x]==x?x:f[x]=find(f[x]);
翻翻资料,也是这么写的。。。。魔鬼藏在细节里。
#include<cstring> #include<cstdio> #include<iostream> #include<algorithm> using namespace std; #define N 100005 struct node { int x,y; int z; bool operator < (const node &e)const { return z<e.z; } }a[N]; int n,m; long long f[N]; int find(int x) { return f[x]==x?x:f[x]=find(f[x]); } int main() { int i,j,x; scanf("%d%d",&n,&m); for(i = 1 ; i <= n ; i++) f[i]= i; for(i = 1; i <= m ; i++) scanf("%d%d%d",&a[i].x,&a[i].y,&a[i].z); sort(a+1,a+1+m); long long sum = 0 ; int k = 0 ; for( i = 1 ; i <= m ; i++) { int xx = find(a[i].x); int yy = find(a[i].y); if(xx!=yy ) { k++; f[xx]=yy; sum+=a[i].z; if(k==n-1) break; } } printf("%lld\n",sum); return 0; }