BZOJ 5415: [Noi2018]归程(kruskal重构树)
##解题思路
$NOI2018$的$Day1$ \(T1\),当时打网络赛的时候不会做。学了一下$kruskal$重构树后发现问题迎刃而解了。根据$kruskal$的性质,如果要找从$u$出发,所走边权$>lim$的所能到达的点,可以将边从大到小排序,重构树后从$u$往上跳到点权$>lim$深度最浅的点,这个点子树的叶节点为所求点集合。有了这个以后就可以跑一遍从$1$开始的最短路,记$Min(i)$表示重构树上$i$这个节点所有子树到$1$的最小值。然后对于每次询问,把刚才所说的深度最浅的点找出来,它的$Min$即为答案。
##代码
#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<queue>
using namespace std;
const int N=400005;
typedef long long LL;
inline int rd(){
int x=0,f=1;char ch=getchar();
while(!isdigit(ch)) f=ch=='-'?0:1,ch=getchar();
while(isdigit(ch)) x=(x<<1)+(x<<3)+ch-'0',ch=getchar();
return f?x:-x;
}
int n,m,q,K,S,w[N],f[N][22],T,val[N<<1];
int head[N],cnt,to[N<<1],nxt[N<<1],F[N],tot,num;
LL ans,Min[N];
struct Edge{
int u,v,a,l;
friend bool operator<(const Edge A,const Edge B){
return A.a>B.a;
}
}edge[N];
struct Node{
int id; LL w;
friend bool operator<(const Node A,const Node B){
return A.w>B.w;
}
Node(int _id=0,int _w=0) {id=_id; w=_w;}
};
priority_queue<Node> Q;
inline void add(int bg,int ed,int w){
to[++cnt]=ed,nxt[cnt]=head[bg],val[cnt]=w,head[bg]=cnt;
}
int get(int x){
if(x==F[x]) return x;
return F[x]=get(F[x]);
}
inline void init(){
tot=num=ans=cnt=0;
for(int i=1;i<=n;i++) F[i]=i;
memset(head,0,sizeof(head));
memset(f,0,sizeof(f));
}
inline void dijkstra(){
memset(Min,0x3f,sizeof(Min));
Q.push(Node(1,0));Min[1]=0; Node now;
while(Q.size()){
now=Q.top();Q.pop();
int x=now.id; if(Min[x]!=now.w) continue;
for(int i=head[x];i;i=nxt[i]){
int u=to[i];
if(Min[x]+val[i]<Min[u]){
Min[u]=Min[x]+val[i];
Q.push(Node(u,Min[u]));
}
}
}
}
inline void build(){
for(int i=1;i<=m;i++){
edge[i].u=rd(),edge[i].v=rd(),edge[i].l=rd(),edge[i].a=rd();
add(edge[i].u,edge[i].v,edge[i].l); add(edge[i].v,edge[i].u,edge[i].l);
}
dijkstra(); sort(edge+1,edge+1+m); int x,y;
cnt=0; memset(head,0,sizeof(head)); num=n;
for(int i=1;i<=m;i++){
x=get(edge[i].u); y=get(edge[i].v);
if(x==y) continue;
num++; F[num]=F[x]=F[y]=num;
add(num,x,0); add(num,y,0);
w[num]=edge[i].a; tot++;
if(tot==n-1) break;
}
}
void dfs(int x,int fa){
f[x][0]=fa;
for(int i=1;i<=19;i++)
f[x][i]=f[f[x][i-1]][i-1];
for(int i=head[x];i;i=nxt[i])
dfs(to[i],x),Min[x]=min(Min[x],Min[to[i]]);
}
int query(int x,int lim){
for(int i=19;~i;i--)
if(f[x][i] && w[f[x][i]]>lim) x=f[x][i];
return Min[x];
}
inline void work(){
int x=rd(),y=rd();
x=(x+ans*K%n-1+n)%n+1;
y=(y+ans*K%(S+1))%(S+1);
ans=query(x,y);
printf("%lld\n",ans);
}
int main(){
T=rd();
while(T--){
n=rd(),m=rd();
init(); build(); dfs(num,0);
q=rd(); K=rd(); S=rd();
while(q--) work();
}
return 0;
}
BZOJ 5415: [Noi2018]归程(kruskal重构树)的更多相关文章
- [NOI2018]归程 kruskal重构树
[NOI2018]归程 LG传送门 kruskal重构树模板题. 另一篇文章里有关于kruskal重构树更详细的介绍和更板子的题目. 题意懒得说了,这题的关键在于快速找出从查询的点出发能到达的点(即经 ...
- [洛谷P4768] [NOI2018]归程 (kruskal重构树模板讲解)
洛谷题目链接:[NOI2018]归程 因为题面复制过来有点炸格式,所以要看题目就点一下链接吧\(qwq\) 题意: 在一张无向图上,每一条边都有一个长度和海拔高度,小\(Y\)的家在\(1\)节点,并 ...
- LOJ.2718.[NOI2018]归程(Kruskal重构树 倍增)
LOJ2718 BZOJ5415 洛谷P4768 Rank3+Rank1无压力 BZOJ最初还不是一道权限题... Update 2019.1.5 UOJ上被hack了....好像是纯一条链的数据过不 ...
- BZOJ5415[Noi2018]归程——kruskal重构树+倍增+堆优化dijkstra
题目描述 本题的故事发生在魔力之都,在这里我们将为你介绍一些必要的设定. 魔力之都可以抽象成一个 n 个节点.m 条边的无向连通图(节点的编号从 1 至 n).我们依次用 l,a 描述一条边的长度.海 ...
- 洛谷P4768 [NOI2018]归程(Kruskal重构树)
题意 直接看题目吧,不好描述 Sol 考虑暴力做法 首先预处理出从$1$到每个节点的最短路, 对于每次询问,暴力的从这个点BFS,从能走到的点里面取$min$ 考虑如何优化,这里要用到Kruskal重 ...
- BZOJ_5415_[Noi2018]归程_kruscal重构树+倍增+最短路
BZOJ_5415_[Noi2018]归程_kruscal重构树+倍增 Description www.lydsy.com/JudgeOnline/upload/noi2018day1.pdf 好久不 ...
- NOI Day1T1归程(Kruskal重构树+Dijkstra)
NOI Day1T1归程(Kruskal重构树+Dijkstra) 题目 洛谷题目传送门 题解 其实我不想写......,所以...... 挖个坑......我以后一定会补的 luogu的题解讲的还是 ...
- #2718. 「NOI2018」归程 kruskal重构树
链接 https://loj.ac/problem/2718 思路 我们希望x所在的连通块尽量的大,而且尽量走高处 离线的话可以询问排序,kruskal过程中更新答案 在线就要用kruskal重构树 ...
- loj2718 「NOI2018」归程[Kruskal重构树+最短路]
关于Kruskal重构树可以翻阅本人的最小生成树笔记. 这题明显裸的Kruskal重构树. 然后这题限制$\le p$的边不能走,实际上就是要满足走最小边权最大的瓶颈路,于是跑最大生成树,构建Krus ...
随机推荐
- JavaScript中的编码解码
1.URI 统一资源标识符(URI)是一个用于标识某一互联网资源名称的字符串.,该种标识允许用户对任何(包括本地和互联网)的资源通过特定的协议进行交互操作.Web上可用的每种资源 -HTML文档.图像 ...
- Python基础教程(021)--Pycharm简介
前言 学习Pycharm开发工具 内容 项目:就是一个功能复杂的软件 目标 必须掌握的工具
- 20180914-Java实例03
Java 实例 – 字符串性能比较测试 以下实例演示了通过两种方式创建字符串,并测试其性能: // StringComparePerformance.java 文件 public class Stri ...
- mysql实现“存在即更新,不存在即插入”
方法1:使用replace关键字 replace是insert的增强版,可以实现插入的数据和已存在的数据发生主键或者唯一键重复,则删除已存在的数据,再实现插入,如果不重复,则直接插入数据. 结合Myb ...
- python之正则表达式(re模块)用法总结
用一句表示正则表达式,就是 字符串的模糊 匹配
- (转)Docker 网络
转:https://www.cnblogs.com/allcloud/p/7150564.html 本系列文章将介绍 Docker的相关知识: (1)Docker 安装及基本用法 (2)Docker ...
- Caused by: java.lang.ClassNotFoundException: com.mchange.v2.cfg.MConfig
出错原因:c3p0 为0.9.5.2版本 而使用了 mchange-commons-java 的版本为0.2.3.4,mchange-commons-java 的版本太高了, 将mchange-com ...
- Python笔记(八)_内部函数与闭包
内部函数 在函数内部定义另一个函数,也就是函数的嵌套 在外部函数的作用域内,外部函数可以随意调用内部函数 由于内部函数的整个定义过程都在外部函数中,所以出了外部函数就无法再被调用了 def outsi ...
- fabric && cita 调研对比
fabric && cita 调研 总结 若计划完全依赖上游的基础功能而不做任何改造,建议选择 fabric:否则,应选择 cita,针对自身业务场景进行持续优化. 一.功能 1.可扩 ...
- 初识redis基础
一.redis 的五大数据类型: 1.String(字符串): 2.List(列表): 3.Set(集合): 4.Hash(哈希,类似于Java里的Map); 5.Zset(sorted set:有序 ...