题目:luogu4234.
题目大意:给定一张nnn个点mmm条边无向图,求这张无向图最大边和最小边的最小权值差.
1≤n≤5∗104,1≤m≤2∗1051\leq n\leq 5*10^4,1\leq m\leq 2*10^51≤n≤5∗104,1≤m≤2∗105.

首先,我们明确一点,一棵最小生成树上的最大边一定最小,这一点很容易用kruskal的算法流程来证明.

那么我们就可以考虑一个暴力算法,枚举一棵生成树的最小边,然后依照kruskal算法加入剩下的边来组成生成树,取最优即可.时间复杂度O(m2log⁡n)O(m^2\log n)O(m2logn).

考虑如何优化这个算法,我们发现枚举的过程不太可能去掉,并查集的时间复杂度去掉没有多大意义,所以我们选择优化每一棵生成树的生成过程.

我们考虑,当我们枚举到一条边时,若我们当前维护的边集中加入这条边不会形成环,我们就将这条边加入.否则我们找到一条形成的环上边权最小的边,然后删掉这条边加入当前的边.当我们维护的边集组成一棵生成树的时候,我们就可以更新答案.

那么我们考虑一棵LCT来维护这道题的这棵带删除和查询链上最小值的并查集即可.

至于维护边权的LCT,拆点维护即可.

代码如下:

#include<bits/stdc++.h>using namespace std;
#define Abigail inline void
const int N=50000,M=200000,INF=1<<29;
struct tree{int x,min,g,fa,s[2],rev;
}tr[N+M+9];
int tmp[N+M+9],ttmp;
int n,m,ans=INF,use[M+9];
struct side{int x,y,v;bool operator < (const side &p)const{return v<p.v;}
}e[M+9];
bool Isroot(int x){return tr[tr[x].fa].s[0]^x&&tr[tr[x].fa].s[1]^x;}
void Pushup(int x){int ls=tr[x].s[0],rs=tr[x].s[1];if (tr[ls].min<tr[rs].min&&tr[ls].min<tr[x].x) tr[x].min=tr[ls].min,tr[x].g=tr[ls].g;else if (tr[rs].min<tr[x].x) tr[x].min=tr[rs].min,tr[x].g=tr[rs].g;else tr[x].min=tr[x].x,tr[x].g=x;
}
void Update_rev(int x){tr[x].rev^=1;swap(tr[x].s[0],tr[x].s[1]);}
void Pushdown(int x){if (!tr[x].rev) return;tr[x].rev=0;Update_rev(tr[x].s[0]);Update_rev(tr[x].s[1]);
}
void Rotate(int x){int y=tr[x].fa,z=tr[y].fa,k=tr[y].s[1]==x;if (!Isroot(y)) tr[z].s[tr[z].s[1]==y]=x;tr[x].fa=z;tr[y].s[k]=tr[x].s[k^1];if (tr[x].s[k^1]) tr[tr[x].s[k^1]].fa=y;tr[x].s[k^1]=y;tr[y].fa=x;Pushup(y);Pushup(x);
}
void Splay(int x){int y,z;tmp[ttmp=1]=x;for (int i=x;!Isroot(i);i=tr[i].fa) tmp[++ttmp]=tr[i].fa;for (;ttmp;ttmp--) Pushdown(tmp[ttmp]);while (!Isroot(x)){y=tr[x].fa,z=tr[y].fa;if (!Isroot(y)) tr[y].s[1]==x^tr[z].s[1]==y?Rotate(x):Rotate(y);Rotate(x);}Pushup(x);
}
void Access(int x){for (int t=0;x;t=x,x=tr[x].fa)Splay(x),tr[x].s[1]=t,Pushup(x);
}
void Makeroot(int x){Access(x);Splay(x);Update_rev(x);}
int Root(int x){Access(x);Splay(x);while (tr[x].s[0]) x=tr[x].s[0];return x;}
void Split(int x,int y){Makeroot(x);Access(y);Splay(y);}
void Link(int x,int y){if (Root(x)==Root(y)) return;Makeroot(x);tr[x].fa=y;}
void Cut(int x,int y){Split(x,y);if (tr[y].s[0]^x||tr[y].s[1]||tr[x].s[1]) return;tr[y].s[0]=tr[x].fa=0;}
int Query_g(int x,int y){Split(x,y);return tr[y].g;}
Abigail into(){scanf("%d%d",&n,&m);for (int i=0;i<=n;i++) tr[i].x=tr[i].min=INF;for (int i=1;i<=m;i++)scanf("%d%d%d",&e[i].x,&e[i].y,&e[i].v);
}
Abigail work(){sort(e+1,e+1+m);int h=1,cnt=1;for (int i=1;i<=m;i++) tr[i+n].x=e[i].v;for (int i=1;i<=m;i++)if (Root(e[i].x)^Root(e[i].y)){Link(e[i].x,i+n);Link(e[i].y,i+n);use[i]=1;while (!use[h]) ++h;if (++cnt==n) ans=min(ans,e[i].v-e[h].v);}else{if (e[i].x==e[i].y) continue;int g=Query_g(e[i].x,e[i].y)-n;Cut(e[g].x,g+n);Cut(e[g].y,g+n);use[g]=0;Link(e[i].x,i+n);Link(e[i].y,i+n);use[i]=1;while (!use[h]) ++h;if (cnt==n) ans=min(ans,e[i].v-e[h].v);}
}
Abigail outo(){printf("%d\n",ans);
}
int main(){into();work();outo();return 0;
}

洛谷4234最小差值生成树题解(最小生成树+LCT)相关推荐

  1. 洛谷.4234.最小差值生成树(LCT)

    题目链接 先将边排序,这样就可以按从小到大的顺序维护生成树,枚举到一条未连通的边就连上,已连通则(用当前更大的)替换掉路径上最小的边,这样一定不会更差. 每次构成树时更新答案.答案就是当前边减去生成树 ...

  2. [洛谷P4234]最小差值生成树

    给定一个标号为从$1$到$n$的.有$m$条边的无向图,求边权最大值与最小值的差值最小的生成树. 做法类似魔法森林,首先求出来最小生成树,然后每次加入一条边,断掉环上最小边并更新答案 这个过程我用两个 ...

  3. 洛谷P5633 最小度限制生成树 题解

    洛谷P5633 最小度限制生成树 题解 题目链接:P5633 最小度限制生成树 题意: 给你一个有 n n n 个节点, m m m 条边的带权无向图,你需要求得一个生成树,使边权总和最小,且满足编号 ...

  4. 洛谷P2619 [国家集训队]Tree I 题解

    洛谷P2619 [国家集训队]Tree I 题解 题目链接:P2619 [国家集训队]Tree I 题意: 给你一个无向带权连通图,每条边是黑色或白色.让你求一棵最小权的恰好有 need\text{n ...

  5. 洛谷P1282 多米诺骨牌 题解

    洛谷P1282 多米诺骨牌 题解 题目链接:P1282 多米诺骨牌 题意: 多米诺骨牌由上下 222 个方块组成,每个方块中有 1∼61\sim61∼6 个点.现有排成行的上方块中点数之和记为 S1S ...

  6. 洛谷P3237 [HNOI2014]米特运输 题解

    洛谷P3237 [HNOI2014]米特运输 题解 题目链接:P3237 [HNOI2014]米特运输 题意: 这题面是真的长啊 qwq 米特是D星球上一种非常神秘的物质,蕴含着巨大的能量.在以米特为 ...

  7. 洛谷P5520 [yLOI2019] 青原樱 题解

    洛谷P5520 [yLOI2019] 青原樱 题解 题目链接:P5520 [yLOI2019] 青原樱 题意: n n n 个空放 m m m 个物品,两两物品不能直接相邻,至少空一格 纯数学题. 看 ...

  8. 洛谷P4084 [USACO17DEC]Barn Painting G 题解

    洛谷P4084 [USACO17DEC]Barn Painting G 题解 题目链接:P4084 [USACO17DEC]Barn Painting G 题意:题意:给定一颗N个节点组成的树,3种颜 ...

  9. 洛谷P4315 月下“毛景树” 题解

    洛谷P4315 月下"毛景树" 题解 题目链接:P4315 月下"毛景树" 题意:请维护一个数据结构,支持 改第 kkk 条边的边权 结点 uuu 到 vvv ...

  10. 洛谷P3412 仓鼠找$Sugar\ II$题解(期望+统计论?)

    洛谷P3412 仓鼠找\(Sugar\ II\)题解(期望+统计论?) 标签:题解 阅读体验:https://zybuluo.com/Junlier/note/1327573 原题链接:洛谷P3412 ...

最新文章

  1. 人工肌肉重大突破登上 Science!多国科学家联合实现全新驱动机
  2. 太绝了,赠你34张网络知识架构思维导图
  3. englishpod主持人对话文本_Englishpod 69 | 主持人文本讲解 | How Would You Like Your Eggs?...
  4. Theano mnist数据集格式
  5. System Center 2012 Process Automatic
  6. python学习04
  7. 《统计学》学习笔记之参数估计
  8. linux usb声卡 submit urb,linux usb urb详解
  9. Device eth0 does not seem to be present,delaying initialization的解决办法
  10. PPT将立方体形状变为很薄的长方体
  11. Java 打印目录结构
  12. 手机桌面没有计算机图标,手机桌面图标不见了,更改桌面图标的大小-
  13. 向云上迁移数据时如何避免停机和中断
  14. Linux系统下载Unity-Tweek-Tool
  15. 计算机语言学方面的期刊.,自然语言处理投稿哪些sci期刊
  16. Java-你知道String为什么不可变吗?
  17. Android游戏开发教程
  18. HTTP接口测试工具及使用
  19. 一个好的导演拍不了一场好戏--校园路-访谈戴谢宁总结(2005.5)
  20. oracle找回删除过的数据吗,oracle数据库中找回删除且已提交的数据

热门文章

  1. Apache Doris ODBC mysql外表注意事项
  2. xpath helper用法
  3. 安卓Tv端App开发与手机端的开发的区别
  4. linux u盘 引导修复工具下载,win7+ubuntu双系统引导修复工具boot repair disk 32+64位ISO版...
  5. 搜索引擎-应用篇(地理位置查询)
  6. 三国志战略版:魏国新黑科技,程昱春华满宠
  7. java流和循环 效率_Java stream 和 for循环效率对比问题
  8. 查看MySQL初始密码并修改
  9. webview的白屏,和硬件加速
  10. 致新浪科技频道的一封公开信