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最小生成树算法(堆优化)的更多相关文章

  1. hiho一下 第二十九周 最小生成树三·堆优化的Prim算法【14年寒假弄了好长时间没搞懂的prim优化:prim算法+堆优化 】

    题目1 : 最小生成树三·堆优化的Prim算法 时间限制:10000ms 单点时限:1000ms 内存限制:256MB 描述 回到两个星期之前,在成功的使用Kruscal算法解决了问题之后,小Ho产生 ...

  2. 图论——最小生成树prim+邻接表+堆优化

    今天学长对比了最小生成树最快速的求法不管是稠密图还是稀疏图,prim+邻接表+堆优化都能得到一个很不错的速度,所以参考学长的代码打出了下列代码,make_pair还不是很会,大体理解的意思是可以同时绑 ...

  3. Prim 最小生成树算法

    Prim 算法是一种解决最小生成树问题(Minimum Spanning Tree)的算法.和 Kruskal 算法类似,Prim 算法的设计也是基于贪心算法(Greedy algorithm). P ...

  4. 最短路模板(Dijkstra & Dijkstra算法+堆优化 & bellman_ford & 单源最短路SPFA)

    关于几个的区别和联系:http://www.cnblogs.com/zswbky/p/5432353.html d.每组的第一行是三个整数T,S和D,表示有T条路,和草儿家相邻的城市的有S个(草儿家到 ...

  5. Prim算法堆优化

    #include <stdio.h> #include <string.h> #include <stdlib.h> #include <ctype.h> ...

  6. P3366 【模板】最小生成树(堆优化prim)

    堆优化prim #include<cstdio> #include<cstring> #include<queue> using namespace std; st ...

  7. Dijkstra算法堆优化

    转自 https://blog.csdn.net/qq_41754350/article/details/83210517 再求单源最短路径时,算法有优劣之分,个人认为在时间方面 朴素dijkstra ...

  8. Dijkstra算法堆优化详解

    DIJ算法的堆优化 DIJ算法的时间复杂度是\(O(n^2)\)的,在一些题目中,这个复杂度显然不满足要求.所以我们需要继续探讨DIJ算法的优化方式. 堆优化的原理 堆优化,顾名思义,就是用堆进行优化 ...

  9. 最短路-朴素版Dijkstra算法&堆优化版的Dijkstra

    朴素版Dijkstra 目标 找到从一个点到其他点的最短距离 思路 ①初始化距离dist数组,将起点dist距离设为0,其他点的距离设为无穷(就是很大的值) ②for循环遍历n次,每层循环里找出不在S ...

随机推荐

  1. Docker的三种网络代理配置

    开源Linux 长按二维码加关注~ 上一篇:IPv6技术白皮书(附PDF下载) 有时因为网络原因,比如公司NAT,或其它啥的,需要使用代理.Docker的代理配置,略显复杂,因为有三种场景.但基本原理 ...

  2. Linux强制用户首次登录修改密码

    一个执着于技术的公众号 地方 前言 Linux强制用户首次登陆修改密码,这应该是RHCE认证中用户管理部分, 属于很基础的内容了.可是我忘记了,所以就有了下面的记录~ 实验过程 1.创建用户并设置登录 ...

  3. .NET混合开发解决方案6 检测是否已安装合适的WebView2运行时

    系列目录     [已更新最新开发文章,点击查看详细] 长青版WebView2运行时将作为Windows 11操作系统的一部分包含在内.但是在Windows 11之前(Win10.Win8.1.Win ...

  4. 手脱MoleBox(2.3.3-2.6.4)

    1.查壳 2.找到OEP 对第二个Call使用ESP定律,再跳转后的位置进入第一个Call,这里就是OEP了,在这里直接dump的话会失败,那是因为MoleBox壳对IAT进行二次跳转,我们先在OEP ...

  5. spring boot 集成 rabbitmq 指南

    先决条件 rabbitmq server 安装参考 一个添加了 web 依赖的 spring boot 项目 我的版本是 2.5.2 添加 maven 依赖 <dependency> &l ...

  6. HttpContext.TraceIdentifier那严谨的设计

    前言 Asp.Net Core中有一个不受人重视的属性HttpContext.TraceIdentifier,它在链路追踪中非常有用,下面是官方的定义: 在项目中一般会将该字段输出到每一条日志中,也可 ...

  7. 好客租房11-为什么脚手架使用jsx语法

    为什么脚手架中可以使用jsx语法 1jsx不是标准的ECMAScript ,他是ECMAScript的语法扩展 2需要使用babel编译处理后 才能在浏览器环境中使用 3create-react-ap ...

  8. 【系统】Windows相关软件下载

    Windows相关软件下载 Visual Studio Windows SQL Server https://my.visualstudio.com/Downloads/Featured?mkt=zh ...

  9. 【FineBI】FineBI连接阿里云mysql教程

    因为某些原因需要查看数据信息,之前连接成功一次,今天软件更新了以后发现连接信息丢. 又重新折腾了一下. 主要有2个地方: 1.查看阿里云数据库外网连接地址:打开云数据库RDS-实例列表-管理-数据库连 ...

  10. Hadoop配置与安装

    基础配置 1.关闭防火墙 systemctl stop firewalld.service #停止firewall systemctl disable firewalld.service #禁止fir ...