克鲁斯卡尔(kruskal)法求最小生成树
来源:互联网 发布:淘宝打包能学到什么 编辑:程序博客网 时间:2024/05/19 12:11
kruskal
基本思想:
克鲁斯卡尔算法的基本思想是以边为主导地位,始终选择当前可用(所选的边不能构成回路)的最小权植边。所以Kruskal算法的第一步是给所有的边按照从小到大的顺序排序。这一步可以直接使用库函数qsort或者sort。接下来从小到大依次考察每一条边(u,v)。
具体实现过程如下:
<1> 设一个有n个顶点的连通图为G(V,E),最初先构造一个只有n个顶点,没有边的非连通图T={V,空}。 <2> 在G中选择一条具有最小权植的边时,若该边的两个顶点在T中连接不会形成环(环可以用并查集判断(是否为同一个祖先)),则将此边加入到T中;否则,将此边舍去(此后永不选用这条边),重新选择一条权植最小的边。(可以先排序) <3> 如此重复下去,直到所有顶点在连通为止。
#include<bits/stdc++.h>using namespace std;int v[10000010];struct node{ long long int u,v,w;} a[10000010];long long int cmp(node a,node b){ return a.w<b.w;}long long int dd(int x) // 使用并查集{ return v[x]==x?v[x]:v[x]=dd(v[x]);}long long int f(int a,int b){ long long int x=dd(a),y=dd(b); if(x!=y) { v[y]=x; return 1; } else return 0;}int main(){ long long int i,n,m,s=0,temp=0; scanf("%lld%lld",&n,&m); for(i=0; i<=n+2; i++) v[i]=i; for(i=1; i<=m; i++) { scanf("%lld%lld%lld",&a[i].u,&a[i].v,&a[i].w); } sort(a+1,a+1+m,cmp);// 边从小到大排 for(i=1; i<=m; i++) { if(temp==n-1) break;//temp表示加入的边的条数,如有n-1条且无环,,则此图定为一棵树 if(f(a[i].u,a[i].v))//祖先不为同一个,,不会形成环 { temp++; s+=a[i].w; } } printf("%lld",s); return 0;}
阅读全文
0 0
- 克鲁斯卡尔(kruskal)法求最小生成树
- 克鲁斯卡尔(Kruskal)算法求最小生成树
- 克鲁斯卡尔(Kruskal)算法求最小生成树
- 克鲁斯卡尔(Kruskal)算法求最小生成树
- 求最小生成树_克鲁斯卡尔算法(Kruskal)
- 克鲁斯卡尔(Kruskal)算法求最小生成树
- 求最小生成树的克鲁斯卡尔(Kruskal)算法
- 最小生成树 克鲁斯卡尔(Kruskal)算法求最小生成树
- 克鲁斯卡尔(Kruskal)算法求解最小生成树
- 最小生成树之克鲁斯卡尔(kruskal)算法
- 最小生成树之Kruskal(克鲁斯卡尔)算法
- 最小生成树-克鲁斯卡尔算法(Kruskal)
- 最小生成树 Kruskal(克鲁斯卡尔)算法
- 最小生成树之克鲁斯卡尔(Kruskal)算法
- 最小生成树-kruskal算法(克鲁斯卡尔算法)
- 克鲁斯卡尔求最小生成树
- 克鲁斯卡尔(Kruskal)算法求图的最小生成树
- Kruskal算法(克鲁斯卡尔算法)---求加权连通图的最小生成树的算法
- sql语句中的left join,right join,inner join的区别
- D3D11 法线贴图(凹凸贴图)
- 实现一个函数,打印乘法口诀表,口诀表的行数和列数自己指定
- 队列详解——循环队列(顺序结构),链队列,循环队列(只有尾指针),字符队列(顺序结构)
- 如何将 Debian Linux 中的默认的 Python 版本切换为替代版本
- 克鲁斯卡尔(kruskal)法求最小生成树
- Linux系统下的用户管理及权利下放
- [贪心] 51Nod1476 括号序列的最小代价
- 一、JDK下载以及环境变量配置
- 封装类
- 搜索巨合集
- Zookeeper 本地模拟伪集群环境(一 leader 多 follower)
- 类行为型模式——模板方法(TemplateMethod)
- ionic购物车框架模板