[BZOJ2594] [WC2006]水管局长(Kruskal+LCT)
[BZOJ2594] [WC2006]水管局长(Kruskal+LCT)
题面
SC省MY市有着庞大的地下水管网络,嘟嘟是MY市的水管局长(就是管水管的啦),嘟嘟作为水管局长的工作就是:每天供水公司可能要将一定量的水从x处送往y处,嘟嘟需要为供水公司找到一条从A至B的水管的路径,接着通过信息化的控制中心通知路径上的水管进入准备送水状态,等到路径上每一条水管都准备好了,供水公司就可以开始送水了。嘟嘟一次只能处理一项送水任务,等到当前的送水任务完成了,才能处理下一项。
在处理每项送水任务之前,路径上的水管都要进行一系列的准备操作,如清洗、消毒等等。嘟嘟在控制中心一声令下,这些水管的准备操作同时开始,但由于各条管道的长度、内径不同,进行准备操作需要的时间可能不同。供水公司总是希望嘟嘟能找到这样一条送水路径,路径上的所有管道全都准备就绪所需要的时间尽量短。嘟嘟希望你能帮助他完成这样的一个选择路径的系统,以满足供水公司的要求。另外,由于MY市的水管年代久远,一些水管会不时出现故障导致不能使用,你的程序必须考虑到这一点。
不妨将MY市的水管网络看作一幅简单无向图(即没有自环或重边):水管是图中的边,水管的连接处为图中的结点。
分析
要求路径上的所有管道全都准备就绪所需要的时间尽量短,实际上就是让最长的边尽量短,显然就是要求一个动态的最小生成树。删边不容易处理,考虑离线转化成动态加边。每加入一条边\((u,v,w)\),就在原来的最小生成树上查询\(u\)到\(v\)路径上的最长边\(k\).如果\(w<k\),就把那条最长边删掉,换成\(w\).否则不进行任何操作。
显然需要用LCT,但是LCT是维护点的,我们可以把边看成一个点。对于第\(i\)条边\((u,v,w)\),我们\(link(u,i+n),link(v,i+n)\),并把\(i+n\)的点权设为\(w\).其他点的点权均为0.然后在LCT上维护点权最大点的点的编号
代码
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<map>
#include<utility>
#define maxn 1000
#define maxm 100000
#define maxq 100000
using namespace std;
int n,m,p;
struct edge{
int from;
int to;
int len;
bool is_del;
friend bool operator < (edge p,edge q){
return p.len<q.len;
}
}E[maxm+5];
map< pair<int,int> , int> id;
struct oper{
int type;
int x;
int y;
int id;
int ans;
}q[maxq+5];
struct link_cut_tree{
#define fa(x) (tree[x].fa)
#define lson(x) (tree[x].ch[0])
#define rson(x) (tree[x].ch[1])
struct node{
int fa;
int ch[2];
int revm;
int id;
int maxid;
}tree[maxn+maxm+5];
inline bool is_root(int x){
return !(lson(fa(x))==x||rson(fa(x))==x);
}
inline int check(int x){
return rson(fa(x))==x;
}
void push_up(int x){
tree[x].maxid=tree[x].id;
if(E[tree[lson(x)].maxid].len>E[tree[x].maxid].len) tree[x].maxid=tree[lson(x)].maxid;
if(E[tree[rson(x)].maxid].len>E[tree[x].maxid].len) tree[x].maxid=tree[rson(x)].maxid;
}
void reverse(int x){
swap(lson(x),rson(x));
tree[x].revm^=1;
}
void push_down(int x){
if(tree[x].revm){
reverse(lson(x));
reverse(rson(x));
tree[x].revm=0;
}
}
void push_down_all(int x){
if(!is_root(x)) push_down_all(fa(x));
push_down(x);
}
void rotate(int x){
int y=fa(x),z=fa(y),k=check(x),w=tree[x].ch[k^1];
tree[y].ch[k]=w;
tree[w].fa=y;
if(!is_root(y)) tree[z].ch[check(y)]=x;
tree[x].fa=z;
tree[x].ch[k^1]=y;
tree[y].fa=x;
push_up(y);
push_up(x);
}
void splay(int x){
push_down_all(x);
while(!is_root(x)){
int y=fa(x);
if(!is_root(y)){
if(check(x)==check(y)) rotate(y);
else rotate(x);
}
rotate(x);
}
push_up(x);
}
void access(int x){
for(int y=0;x;y=x,x=fa(x)){
splay(x);
rson(x)=y;
push_up(x);
}
}
void make_root(int x){
access(x);
splay(x);
reverse(x);
}
void link(int x,int y){
make_root(x);
fa(x)=y;
}
void split(int x,int y){
make_root(x);
access(y);
splay(y);
}
void cut(int x,int y){
split(x,y);
fa(x)=lson(y)=0;
push_up(y);
}
int find_root(int x){
access(x);
splay(x);
while(lson(x)){
push_down(x);
x=lson(x);
}
splay(x);
return x;
}
int Query_edge(int x,int y){
split(x,y);
return tree[y].maxid;
}
inline void Add_edge(int id){
link(E[id].from,id+n);
link(E[id].to,id+n);
}
inline void Del_edge(int id){
cut(E[id].from,id+n);
cut(E[id].to,id+n);
}
}T;
void kruskal(){
for(int i=1;i<=m;i++){
if(!E[i].is_del){
int x=E[i].from,y=E[i].to;
if(T.find_root(x)==T.find_root(y)) continue;
// printf("db: %d\n",id[make_pair(x,y)]);
T.Add_edge(i);
}
}
}
int main(){
// freopen("7.in","r",stdin);
scanf("%d %d %d",&n,&m,&p);
for(int i=1;i<=m;i++){
scanf("%d %d %d",&E[i].from,&E[i].to,&E[i].len);
}
sort(E+1,E+1+m);
for(int i=1;i<=m;i++){
id[make_pair(E[i].from,E[i].to)]=id[make_pair(E[i].to,E[i].from)]=i;
}
for(int i=1;i<=p;i++){
scanf("%d %d %d",&q[i].type,&q[i].x,&q[i].y);
if(q[i].type==2){
int t=id[make_pair(q[i].x,q[i].y)];
q[i].id=t;
E[t].is_del=1;
}
}
for(int i=1;i<=n+m;i++){
if(i<=n) T.tree[i].id=0;
else T.tree[i].id=i-n;
}
kruskal();
for(int i=p;i>=1;i--){
int x=q[i].x,y=q[i].y;
if(q[i].type==1){
q[i].ans=E[T.Query_edge(x,y)].len;
}else{
int pre=T.Query_edge(x,y);
int nex=q[i].id;
if(E[pre].len>E[nex].len){
T.Del_edge(pre);
T.Add_edge(nex);
}
}
}
for(int i=1;i<=p;i++){
if(q[i].type==1) printf("%d\n",q[i].ans);
}
}
[BZOJ2594] [WC2006]水管局长(Kruskal+LCT)的更多相关文章
- [BZOJ2594][WC2006]水管局长加强版(LCT+Kruskal)
2594: [Wc2006]水管局长数据加强版 Time Limit: 25 Sec Memory Limit: 128 MBSubmit: 4452 Solved: 1385[Submit][S ...
- [bzoj2594][Wc2006]水管局长数据加强版 (lct)
论蒟蒻的自我修养T_T.. 和noi2014魔法森林基本一样...然而数据范围大得sxbk...UPD:这题如果用lct判联通的话可能会被卡到O(mlogm)..所以最好还是用并查集吧 一开始数组开太 ...
- BZOJ2594: [Wc2006]水管局长数据加强版
题解: 裸LCT+离线+二分+MST... 代码:(几乎摘抄自hzwer) #include<cstdio> #include<cstdlib> #include<cma ...
- P4172 [WC2006]水管局长(LCT)
P4172 [WC2006]水管局长 LCT维护最小生成树,边权化点权.类似 P2387 [NOI2014]魔法森林(LCT) 离线存储询问,倒序处理,删边改加边. #include<iostr ...
- BZOJ2594 [Wc2006]水管局长数据加强版 【LCT维护最小生成树】
题目 SC省MY市有着庞大的地下水管网络,嘟嘟是MY市的水管局长(就是管水管的啦),嘟嘟作为水管局长的工作就是:每天供水公司可能要将一定量的水从x处送往y处,嘟嘟需要为供水公司找到一条从A至B的水管的 ...
- 洛谷P4172 [WC2006]水管局长(lct求动态最小生成树)
SC省MY市有着庞大的地下水管网络,嘟嘟是MY市的水管局长(就是管水管的啦),嘟嘟作为水管局长的工作就是:每天供水公司可能要将一定量的水从x处送往y处,嘟嘟需要为供水公司找到一条从A至B的水管的路径, ...
- [BZOJ2594] [Wc2006]水管局长数据加强版(LCT + kruskal + 离线)
传送门 WC这个题真是丧心病狂啊,就是想学习一下怎么处理边权,给我来了这么一个破题! ORZ hzwer 临摹黄学长代码233 但还是复杂的一匹 理一下思路吧 题目大意:给定一个无向图,多次删除图中的 ...
- BZOJ2594 [Wc2006]水管局长数据加强版 LCT kruskal
欢迎访问~原文出处——博客园-zhouzhendong 去博客园看该题解 题目传送门 - BZOJ2594 题意概括 N个点的图,M条带权边.(N<=100000,M<=1000000) ...
- [bzoj2594][Wc2006]水管局长数据加强版——lct+离线
Brief Description 您有一个无向带权图,您需要支持两种操作. 询问两个点之间的最大权最小路径. 删除一条边. Algorithm Design 我们首先提出一个猜想:最优路径一定在原图 ...
随机推荐
- 消费端ACK和重回队列
使用场景 消费端ACK和重回队列 消费端ACK使用场景: 1.消费端进行消费的时候,如果由于业务异常我们可以进行日志记录,然后进行补偿. 2.由于服务器宕机等严重问题,那我们就需要手工进行ACK保障消 ...
- 26.Python三目运算符(三元运算符)用法详解
Python 可通过 if 语句来实现三目运算符的功能,因此可以近似地把这种 if 语句当成三目运算符.作为三目运算符的 if 语句的语法格式如下: True_statements if expres ...
- 为什么还需要学习TypeScript
开篇 TypeScript 是由 C#语言的创始人 Anders Hejlsberg 设计的一种编程语言,设计的初衷就是为了帮助 JavaScript 的开发人员能像类似高级语言c#,Java那样编写 ...
- hadoop hdfs hbase优化实例
需求描述: 从hdfs中获取数据,字段url需要计算出url_type 通过进行hive的left outer join ,效率非常低.故将url的类型导入到hbase中,利用hbase快速查询的特点 ...
- 【Java笔试】OYO校招Java工程师|牛客平台,算法:字符串翻转。附选择题解析
文章目录 1.Java笔试算法题:字符串翻转 2.单选题: 2.1.同一进程下的多个线程可以共享哪一种资源:data section 2.2.一个树形的叶结点在前序遍历和后序遍历下,可以相同的相对位置 ...
- php执行方式对比:mod_php&php-fpm
mod_php 1.是apache的附属包,apache死掉后php也会死掉 2.稳定性差,php出错服务器进程也会受影响 php-fpm 1.和nginx是两个独立的个体. 2.php- ...
- cygwin下make指令不存在 & cmd也能用make的配置方法
最近做毕设需要使用Mask R-CNN,就配置了相关环境,在安装pycocotools时要make,于是决定用cygwin来做.但在路径下make时出现了问题: bash错误:make指令不存在.一番 ...
- a标签的伪类
a 超链接 伪类:给元素添加特殊的效果 :link 未访问过的链接初始颜色 :visited 访问过后的链接颜色 :hover 鼠标移入(悬停)时的颜色 :active 鼠标按下时链接的颜色 书写时的 ...
- nvl(sum(字段),0) 的时候,能展示数据0,但是group by 下某个伪列的时候,查不到数据(转载)
今天碰到一个比较有疑惑的问题,就是在统计和的时候,我们往往有时候查不到数据,都会再加个 nvl(sum(字段),0) 来显示这个字段,但是如果我们再加个group by ,就算有加入这个 nvl(nu ...
- 找出所有从根节点到叶子节点路径和等于n的路径并输出
//找出所有从根节点到叶子节点路径和等于n的路径并输出 Stack<Node> stack = new Stack<Node>(); public void findPath( ...