BZOJ3712[PA2014]Fiolki 建图+倍增lca
居然是一道图论题 毫无思路
我们对于每一次的融合操作 \((a,b)\) 建一个新点\(c\) 并向\(a,b\)连边 再将\(b\)瓶当前的位置赋成\(c\) 这样子我们就可以建成一个森林
现在枚举每一种反应\(M_i\) 看他在森林里是否存在\(lca\) 存在就相当于会在\(lca\)处发生反应 因为有反应的顺序 我们对\(lca\)排序后先做\(lca\)深度大的 深度相同就先做\(M\)的\(id\)小的 这样就满足题意了
我交了半天 居然是因为倍增数组写错了 真菜o(╥﹏╥)o
#include<bits/stdc++.h>
using namespace std;
#define FO(x) {freopen(#x".in","r",stdin);freopen(#x".out","w",stdout);}
#define pa pair<int,int>
#define mod 1000000007
#define ll long long
#define mk make_pair
#define pb push_back
#define fi fisrt
#define se second
#define cl(x) memset(x,0,sizeof x)
#ifdef Devil_Gary
#define bug(x) cout<<(#x)<<" "<<(x)<<endl
#define debug(...) fprintf(stderr, __VA_ARGS__)
#else
#define bug(x)
#define debug(...)
#endif
const int INF = 0x7fffffff;
const int N=2e5+5;
//*
char *TT,*mo,but[(1<<15)+2];
#define getchar() ((TT==mo&&(mo=(TT=but)+fread(but,1,1<<15,stdin),TT==mo))?-1:*TT++)//*/
inline int read(){
int x=0,rev=0,ch=getchar();
while(ch<'0'||ch>'9'){if(ch=='-')rev=1;ch=getchar();}
while(ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+ch-'0';ch=getchar();}
return rev?-x:x;
}
struct Edge{
int v,nxt;
}e[N<<1];
struct data{
int u,v,f,dis,id;
}a[N*3];
ll ans;
int g[N],n,cnt,tot,m,K,head[N<<1],dep[N<<1],bin[23]={1},f[N<<1][22],pos[N];
void add(int u,int v){
e[++tot].v=v,e[tot].nxt=head[u],head[u]=tot;
}
bool cmp(const data&a,const data&b){
return a.dis==b.dis?a.id<b.id:a.dis>b.dis;
}
void dfs(int x){
for(int i=1;i<=19&&bin[i-1]<=dep[x];i++) f[x][i]=f[f[x][i-1]][i-1];
for(int i=head[x];i;i=e[i].nxt){
int j=e[i].v;
dep[j]=dep[x]+1,f[j][0]=x,dfs(j);
}
}
int LCA(int u,int v){
if(dep[u]<dep[v]) swap(u,v);
int ret=dep[u]-dep[v];
for(int i=19;~i;--i){
if(bin[i]&ret){
u=f[u][i];
}
}
if(u==v) return u;
for(int i=19;~i;i--){
if(f[u][i]!=f[v][i]){
u=f[u][i],v=f[v][i];
}
}
return f[u][0];
}
int main(){
#ifdef Devil_Gary
freopen("in.txt","r",stdin);
#endif
n=read(),m=read(),K=read();
for(int i=1;i<=20;i++) bin[i]=bin[i-1]<<1;
for(int i=1;i<=n;i++) g[i]=read(),pos[i]=i;
for(int i=1,x,y,z;i<=m;i++) {
x=read(),y=read(),z=n+i;
add(z,pos[x]),add(z,pos[y]),pos[y]=z;
}
for(int i=n+m;i;--i) if(!f[i][0]) dfs(i);
for(int i=1;i<=K;i++){
#define i cnt
a[++i].u=read(),a[i].v=read(),a[i].f=LCA(a[i].u,a[i].v),a[i].dis=dep[a[i].f],a[i].id=i;
#undef i
if(!a[cnt].f) --cnt;
}
sort(a+1,a+cnt+1,cmp);
for(int i=1,u,v,mn;i<=cnt;i++){
if(!a[i].f) continue;
u=a[i].u,v=a[i].v;
mn=min(g[u],g[v]);
g[u]-=mn,g[v]-=mn,ans+=mn;
}
printf("%lld\n",ans<<1);
}
BZOJ3712[PA2014]Fiolki 建图+倍增lca的更多相关文章
- BZOJ3712[PA2014]Fiolki——并查集重构树
题目描述 化学家吉丽想要配置一种神奇的药水来拯救世界.吉丽有n种不同的液体物质,和n个药瓶(均从1到n编号).初始时,第i个瓶内装着g[i]克的第i种物质.吉丽需要执行一定的步骤来配置药水,第i个步骤 ...
- [bzoj3712][PA2014]Fiolki
description 题面 data range \[ 0\le m<n\le 200000,0\le k\le 500000\] solution 之前本人一直煞笔地思考暴力是否可行 考虑按 ...
- 【BZOJ-3712】Fiolki LCA + 倍增 (idea题)
3712: [PA2014]Fiolki Time Limit: 30 Sec Memory Limit: 128 MBSubmit: 303 Solved: 67[Submit][Status] ...
- [bzoj3712][PA2014]Fiolki_倍增LCA
Fiolki bzoj-3712 PA-2014 题目大意:题目链接. 注释:略. 想法: 神题! 我们建树:对于一次倾倒操作,我们弄一个新的大瓶子作为两个合并瓶子的父亲节点,与两个瓶子相连. 对于一 ...
- BZOJ 3712: [PA2014]Fiolki 倍增+想法
3712: [PA2014]Fiolki Time Limit: 30 Sec Memory Limit: 128 MBSubmit: 437 Solved: 115[Submit][Status ...
- BZOJ 4242 水壶(BFS建图+最小生成树+树上倍增)
题意 JOI君所居住的IOI市以一年四季都十分炎热著称. IOI市是一个被分成纵H*横W块区域的长方形,每个区域都是建筑物.原野.墙壁之一.建筑物的区域有P个,编号为1...P. JOI君只能进入建筑 ...
- [十二省联考2019]字符串问题——后缀自动机+parent树优化建图+拓扑序DP+倍增
题目链接: [十二省联考2019]字符串问题 首先考虑最暴力的做法就是对于每个$B$串存一下它是哪些$A$串的前缀,然后按每组支配关系连边,做一遍拓扑序DP即可. 但即使忽略判断前缀的时间,光是连边的 ...
- codevs 1036 商务旅行 (倍增LCA)
/* 在我还不知道LCA之前 暴力跑的SPFA 70分 三个点TLE */ #include<iostream> #include<cstdio> #include<cs ...
- BFS+最小生成树+倍增+LCA【bzoj】4242 水壶
[bzoj4242 水壶] Description JOI君所居住的IOI市以一年四季都十分炎热著称. IOI市是一个被分成纵H*横W块区域的长方形,每个区域都是建筑物.原野.墙壁之一.建筑物的区域有 ...
随机推荐
- Redis记录-redis和memcached的区别
1.Redis和Memcache都是将数据存放在内存中,都是内存数据库.不过memcache还可用于缓存其他东西,例如图片.视频等等: 2.Redis不仅仅支持简单的k/v类型的数据,同时还提供lis ...
- 通达信zig函数的python实现
通达信zig函数的python实现 代码 # coding: utf-8 """ Created on Sat Jan 05 18:53:39 2019 http://w ...
- Java面试题系列(二)Java内存模型
在进行Java编程时,我们通常需要通过new创建一个对象的实例.就比如有一个People的类,那么创建一个People的实例:People w_people = new People(); 此时,ne ...
- AngularJS入门基础——表单验证
<form name="form" novalidata> <label name="email">your email</l ...
- 第12月第30天 love2d
1. Linux On Linux, you can use one of these command lines: love /home/path/to/gamedir/ love /home/pa ...
- 自己动手开发Socks5代理服务器
一.Socks5协议简介 socks5是基于传输层的协议,客户端和服务器经过两次握手协商之后服务端为客户端建立一条到目标服务器的通道,在传输层转发TCP/UDP流量. 关于socks5协议规范,到处都 ...
- object-c 数学计算公式
1. 三角函数 double sin (double);正弦 double cos (double);余弦 double tan (double);正切 2 .反三角函数 double as ...
- redis从入门到踩坑
背景 Redis在互联网项目的使用也是非常普遍的,作为最常用的NO-SQL数据库,对Redis的了解已经成为了后端开发的必备技能.小编对Redis的使用时间不长,但是项目中确两次踩中了Redis的坑, ...
- TAU调研咨询
厦门宇能科技有限公司 GPRS-RTU/DTU.3/4G路由器.无线远程抄表.管网监控 咨询电话:0592-5710250 2017-07-04 9:36:16 您好,欢迎光临.请问有什么可以帮到您? ...
- bulk_write&Replace_one
ns=[]ns.append(ReplaceOne({'ip': ok['ip']}, ok, upsert=True))#更新插入 if len(ns) > 0: res = coll.bul ...