prim最小生成树算法(堆优化)
prim算法原理和dijkstra算法差不多,依然不能处理负边

1 #include<bits/stdc++.h>
2 using namespace std;
3 struct edge
4 {
5 int u,v,w,nxt;
6 };
7 edge e[100010];//建边
8 bool f[110];//判断该点是否被染过色
9 struct node
10 {
11 int dis,t;
12 };
13 node nod[110];//存点
14 int n,cnt,total;// n 点数 cnt 计数器 total 最小生成树的边权和
15 int h[110];//记录每个点发出的最后一条边的编号
16 void add(int,int,int);//函数声明
17 struct cmp
18 {
19 bool operator()(node a,node b)
20 {
21 return a.dis>b.dis;
22 }
23 };//定义比较函数,别忘了';'
24 priority_queue<node,vector<node>,cmp> q;//定义结构体优先队列存点
25 void prim()//堆优化
26 {
27 while(!q.empty()&&cnt<n)//cnt 判断是否达到n-1条边
28 {
29 while(!q.empty()&&f[q.top().t]) q.pop();//判断队首元素是否被标记,若被标记,踢出
30 //加这个的原因是每加一个元素,他不会更新已经在队列中的元素,而是作为新元素加入队列
31 if(q.empty()) break;//如果堆为空,说明都打过标记了,那也就没有继续下去的必要了,退出即可,这里可能会被卡时间
32 node k=q.top();//取队首元素
33 int u=k.t;//取队首元素标号
34 f[u]=1;//打标记
35 total+=nod[u].dis;//记录最小生成树的边权和
36 q.pop();//弹出
37 for(int i=h[u];i;i=e[i].nxt)//邻接表遍历,更新值
38 {
39 int v=e[i].v,w=e[i].w;//取终点和边权
40 if(w<nod[v].dis)//判断边权是否更小
41 {
42 nod[v].dis=w;//更新值
43 q.push(nod[v]);//入队
44 }
45 }
46 cnt++;//记录已经找到了的边的数量
47 }
48 }
49 int main()
50 {
51 scanf("%d",&n);//输入点数
52 for(int i=1;i<=n;++i)
53 {
54 nod[i].dis=0x3f3f3f;//初始化
55 nod[i].t=i;//记录点的标号
56 }
57 for(int i=1;i<=n;++i)
58 {
59 for(int j=1;j<=n;++j)//循环建边,根据题目来
60 {
61 int w;
62 scanf("%d",&w);
63 if(w)
64 {
65 add(i,j,w);//建边
66 add(j,i,w);
67 }
68 }
69 }
70 nod[1].dis=0;//起点到自己的距离是0
71 q.push(nod[1]);//入队
72 cnt=0;//初始化计数器(循环利用)
73 prim();//prim算法
74 printf("%d",total);
75 return 0;//结束
76 }
77 void add(int u,int v,int w)//加边
78 {
79 e[++cnt].u=u;
80 e[cnt].v=v;
81 e[cnt].w=w;
82 e[cnt].nxt=h[u];
83 h[u]=cnt;
84 }
重载运算符版本

1 #include<bits/stdc++.h>
2 #define ll long long
3 #define rll register long long
4 using namespace std;
5 ll n,m,cnt,tot;
6 ll h[5010];
7 bool flag[5010];
8 struct edge
9 {
10 ll u,v,w,nxt;
11 };
12 edge e[400010];
13 struct node
14 {
15 ll t,dis;
16 bool operator < (const node &b) const
17 {
18 return dis>b.dis;
19 }//重载运算符
20 };
21 node nod[5010];
22 priority_queue<node> q;
23 void add(ll,ll,ll);
24 void prim();
25 int main()
26 {
27 scanf("%lld%lld",&n,&m);
28 for(rll i=1;i<=n;++i)
29 {
30 nod[i].dis=0x3f3f3f;
31 nod[i].t=i;
32 }
33 for(rll u,v,w,i=1;i<=m;++i)
34 {
35 scanf("%lld%lld%lld",&u,&v,&w);
36 add(u,v,w);
37 add(v,u,w);
38 }
39 nod[1].dis=0;
40 q.push(nod[1]);
41 cnt=0;
42 prim();
43 printf("%lld",tot);
44 return 0;
45 }
46 void add(ll u,ll v,ll w)
47 {
48 e[++cnt].u=u;
49 e[cnt].v=v;
50 e[cnt].w=w;
51 e[cnt].nxt=h[u];
52 h[u]=cnt;
53 }
54 void prim()
55 {
56 while(!q.empty()&&cnt<n)
57 {
58 while(!q.empty()&&flag[q.top().t]) q.pop();
59 if(q.empty()) break;//上一个代码讲了
60 node g=q.top();
61 ll u=g.t;
62 flag[u]=true;
63 tot+=nod[u].dis;
64 q.pop();
65 for(rll i=h[u];i;i=e[i].nxt)
66 {
67 ll v=e[i].v,w=e[i].w;
68 if(w<nod[v].dis)
69 {
70 nod[v].dis=w;
71 q.push(nod[v]);
72 }
73 }
74 cnt++;
75 }
76 }
prim最小生成树算法(堆优化)的更多相关文章
- hiho一下 第二十九周 最小生成树三·堆优化的Prim算法【14年寒假弄了好长时间没搞懂的prim优化:prim算法+堆优化 】
题目1 : 最小生成树三·堆优化的Prim算法 时间限制:10000ms 单点时限:1000ms 内存限制:256MB 描述 回到两个星期之前,在成功的使用Kruscal算法解决了问题之后,小Ho产生 ...
- 图论——最小生成树prim+邻接表+堆优化
今天学长对比了最小生成树最快速的求法不管是稠密图还是稀疏图,prim+邻接表+堆优化都能得到一个很不错的速度,所以参考学长的代码打出了下列代码,make_pair还不是很会,大体理解的意思是可以同时绑 ...
- Prim 最小生成树算法
Prim 算法是一种解决最小生成树问题(Minimum Spanning Tree)的算法.和 Kruskal 算法类似,Prim 算法的设计也是基于贪心算法(Greedy algorithm). P ...
- 最短路模板(Dijkstra & Dijkstra算法+堆优化 & bellman_ford & 单源最短路SPFA)
关于几个的区别和联系:http://www.cnblogs.com/zswbky/p/5432353.html d.每组的第一行是三个整数T,S和D,表示有T条路,和草儿家相邻的城市的有S个(草儿家到 ...
- Prim算法堆优化
#include <stdio.h> #include <string.h> #include <stdlib.h> #include <ctype.h> ...
- P3366 【模板】最小生成树(堆优化prim)
堆优化prim #include<cstdio> #include<cstring> #include<queue> using namespace std; st ...
- Dijkstra算法堆优化
转自 https://blog.csdn.net/qq_41754350/article/details/83210517 再求单源最短路径时,算法有优劣之分,个人认为在时间方面 朴素dijkstra ...
- Dijkstra算法堆优化详解
DIJ算法的堆优化 DIJ算法的时间复杂度是\(O(n^2)\)的,在一些题目中,这个复杂度显然不满足要求.所以我们需要继续探讨DIJ算法的优化方式. 堆优化的原理 堆优化,顾名思义,就是用堆进行优化 ...
- 最短路-朴素版Dijkstra算法&堆优化版的Dijkstra
朴素版Dijkstra 目标 找到从一个点到其他点的最短距离 思路 ①初始化距离dist数组,将起点dist距离设为0,其他点的距离设为无穷(就是很大的值) ②for循环遍历n次,每层循环里找出不在S ...
随机推荐
- wlile、 for循环和基本数据类型及内置方法
while + else 1.while与else连用 当while没有被关键字break主动结束的情况下 正常结束循环体代码之后执行else的子代码 """ while ...
- unity---对象池
当内存占满了,GC会自动清理内存 优化方法:对象池 Invoke("Push",1);//延迟一秒时间调用 高级缓存池 小池子 大池子
- css属性补充与JS数据类型
目录 溢出属性(overflow) 定位(position) z-index属性 opacity不透明度 JavaScript简介 变量与注释 数据类型 数值(Number) 字符串(String) ...
- 面试官:Dubbo怎么实现服务降级,他有什么好处?
哈喽!大家好,我是小奇,一位热爱分享的程序员 小奇打算以轻松幽默的对话方式来分享一些技术,如果你觉得通过小奇的文章学到了东西,那就给小奇一个赞吧 文章持续更新 一.前言 书接上回,今天周一了,招聘软件 ...
- Ceph集群搭建记录
环境准备 基础环境 node00 192.168.247.144 node00 node01 192.168.247.135 node01 node02 192.168.247.143 node02 ...
- Datax源码改造关键步骤记录
Datax源码改造关键步骤记录: 一.作业配置1.一个job配置:reader 和writer 的column 字段必须是所有表共有的:2.reader多张表,writer一个表时,所有reader的 ...
- 前端3JS2
内容概要 运算符 流程控制 三元运算符 函数 自定义对象 内置对象 JSON对象 正则对象 内容详情 运算符
- Acwing 1927 自动补全(知识点:hash,二分,排序)
读完题目第一想法是trie树 ,不过好像没怎么做过trie树的题,看y总给的知识点是二分排序,所以就有了如下思路: 但是但是,看完其他题解之后才坚定了我的想法,原来真的是这样排序,暴力啊! 具体步骤 ...
- JS:函数的几种写法1
1.构造函数: var fn = new function(); 2.声明式: function fn(){}; 3.匿名函数(又称自调用函数): (function(){})(); 4.表达式: v ...
- 关于使用koa实现线上 https服务
var https=require("https");//https服务var fs= require("fs");var Koa = require('koa ...