[WC2013][luogu4074] 糖果公园 [树上带修改莫队]
题面:
思路:
一道实现起来细节比较恶心的题目
但是其实就是一个裸的树上带修改莫队
好像树上莫队也出不了什么结合题目,不像序列莫队天天结合AC自动机、后缀数组......
莫队学习请戳这里:莫队
Code:
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#define ll long long
using namespace std;
inline ll read(){
ll re=,flag=;char ch=getchar();
while(ch>''||ch<''){
if(ch=='-') flag=-;
ch=getchar();
}
while(ch>=''&&ch<='') re=(re<<)+(re<<)+ch-'',ch=getchar();
return re*flag;
}
struct edge{
ll to,next;
}a[];
ll n,m,Q,first[],cntt,clk,block;
ll fa[],dep[],st[][],dfn[];
ll v[],w[],x[];
inline void add(ll u,ll v){
a[++cntt]=(edge){v,first[u]};first[u]=cntt;
a[++cntt]=(edge){u,first[v]};first[v]=cntt;
}
void dfs(ll u,ll f){
//cout<<"dfs "<<u<<" "<<f<<"\n";
ll i,v;
fa[u]=st[u][]=f;dep[u]=dep[f]+;dfn[u]=++clk;
for(i=first[u];~i;i=a[i].next){
v=a[i].to;
if(v==f) continue;
dfs(v,u);
}
}
void init(){
for(ll i=;i<=;i++){
for(ll j=;j<=n;j++){
st[j][i]=st[st[j][i-]][i-];
}
}
}
void _swap(ll &l,ll &r){l^=r;r^=l;l^=r;}
ll LCA(ll l,ll r){
//cout<<"lca "<<l<<" "<<r<<"\n";
if(dep[l]>dep[r]) _swap(l,r);
ll i;
for(i=;i>=;i--) if(dep[st[r][i]]>=dep[l]) r=st[r][i];
if(l==r) return l;
for(i=;i>=;i--){
if(st[l][i]!=st[r][i]){
l=st[l][i];r=st[r][i];
}
}
return fa[l];
}
ll curl,curr,curc,cntq,cntc,cnt[];bool vis[];
ll ans[],tot;
struct query{
ll l,r,c,i;
}q[];
bool cmp(query l,query r){
if(dfn[l.l]/block!=dfn[r.l]/block) return dfn[l.l]/block<dfn[r.l]/block;
else{
if(dfn[l.r]/block!=dfn[r.r]/block)
return dfn[l.r]/block<dfn[r.r]/block;
else return l.c<r.c;
}
}
struct change{
ll pos,to;
}c[];
void rev(ll i){
if(vis[i]) vis[i]=,tot-=v[x[i]]*w[cnt[x[i]]],cnt[x[i]]--;
else vis[i]=,cnt[x[i]]++,tot+=v[x[i]]*w[cnt[x[i]]];
//cout<<"rev node "<<i<<" "<<x[i]<<" "<<tot<<"\n";
}
void change(ll i){
//cout<<"change node "<<i<<" "<<c[i].pos<<" "<<c[i].to<<"\n";
if(!vis[c[i].pos]) _swap(c[i].to,x[c[i].pos]);
else{
rev(c[i].pos);
_swap(c[i].to,x[c[i].pos]);
rev(c[i].pos);
}
}
int main(){
memset(first,-,sizeof(first));
ll i,t1,t2,t3;
n=read();m=read();Q=read();block=(ll)pow(n,0.60);
for(i=;i<=m;i++) v[i]=read();
for(i=;i<=n;i++) w[i]=read();
for(i=;i<n;i++){
t1=read();t2=read();add(t1,t2);
}
for(i=;i<=n;i++) x[i]=read();
dfs(,);init();
//for(i=1;i<=n;i++) cout<<fa[i]<<" "<<dep[i]<<"\n";
for(i=;i<=Q;i++){
t1=read();t2=read();t3=read();
if(t1) q[++cntq].l=t2,q[cntq].r=t3,q[cntq].c=cntc,q[cntq].i=cntq;
else c[++cntc].pos=t2,c[cntc].to=t3;
//cout<<"finish read in "<<i<<"\n";
}
sort(q+,q+cntq+,cmp);
//for(i=1;i<=cntq;i++)
//cout<<q[i].l<<" "<<q[i].r<<" "<<q[i].c<<" "<<q[i].i<<"\n"; if(dfn[q[].l]>dfn[q[].r]) _swap(q[].l,q[].r);
ll lca=LCA(q[].l,q[].r),l,r;curl=q[].l;curr=q[].r;
l=curl;r=curr;
while(l!=lca) rev(l),l=fa[l];
while(r!=lca) rev(r),r=fa[r];
while(curc<q[].c) change(++curc);
rev(lca);ans[q[].i]=tot;rev(lca);
for(i=;i<=cntq;i++){
//cout<<"i=="<<i<<"\n";
if(dfn[q[i].l]>dfn[q[i].r]) _swap(q[i].l,q[i].r);
lca=LCA(curr,q[i].r);l=curr;r=q[i].r;
while(l!=lca) rev(l),l=fa[l];
while(r!=lca) rev(r),r=fa[r];
lca=LCA(curl,q[i].l);l=curl;r=q[i].l;
while(l!=lca) rev(l),l=fa[l];
while(r!=lca) rev(r),r=fa[r];
while(curc>q[i].c) change(curc--);
while(curc<q[i].c) change(++curc);
lca=LCA(q[i].l,q[i].r);
rev(lca);ans[q[i].i]=tot;rev(lca);
curl=q[i].l;curr=q[i].r;
}
for(i=;i<=cntq;i++) printf("%lld\n",ans[i]);
}
[WC2013][luogu4074] 糖果公园 [树上带修改莫队]的更多相关文章
- luogu4074 [WC2013]糖果公园(树上带修莫队)
link 题目大意:给一个树,树上每个点都有一种颜色,每个颜色都有一个收益 每次修改一个点上的颜色 或询问一条链上所有颜色第i次遇到颜色j可以获得w[i]*v[j]的价值,求链上价值和 题解:树上带修 ...
- LUOGU P4074 [WC2013]糖果公园 (树上带修莫队)
传送门 解题思路 树上带修莫队,搞了两天..终于开O2+卡常大法贴边过了...bzoj上跑了183s..其实就是把树上莫队和带修莫队结合到一起,首先求出括号序,就是进一次出一次那种的,然后如果求两个点 ...
- 【BZOJ-3052】糖果公园 树上带修莫队算法
3052: [wc2013]糖果公园 Time Limit: 200 Sec Memory Limit: 512 MBSubmit: 883 Solved: 419[Submit][Status] ...
- [BZOJ4129]Haruna’s Breakfast(树上带修改莫队)
BZOJ3585,BZOJ2120,BZOJ3757三合一. 对于树上路径问题,树链剖分难以处理的时候,就用树上带修改莫队. 这里的MEX问题,使用BZOJ3585的分块方法,平衡了时间复杂度. 剩下 ...
- 【Luogu P4074】[WC2013]糖果公园(树上带修改莫队)
题目描述 Candyland 有一座糖果公园,公园里不仅有美丽的风景.好玩的游乐项目,还有许多免费糖果的发放点,这引来了许多贪吃的小朋友来糖果公园游玩. 糖果公园的结构十分奇特,它由 \(n\) 个游 ...
- bzoj 3052: [wc2013]糖果公园【树上带修改莫队】
参考:http://blog.csdn.net/lych_cys/article/details/50845832 把树变成dfs括号序的形式,注意这个是不包含lca的(除非lca是两点中的一个) 然 ...
- BZOJ.3052.[WC2013]糖果公园(树上莫队 带修改莫队)
题目链接 BZOJ 当然哪都能交(都比在BZOJ交好),比如UOJ #58 //67376kb 27280ms //树上莫队+带修改莫队 模板题 #include <cmath> #inc ...
- 【BZOJ】3052: [wc2013]糖果公园 树分块+带修改莫队算法
[题目]#58. [WC2013]糖果公园 [题意]给定n个点的树,m种糖果,每个点有糖果ci.给定n个数wi和m个数vi,第i颗糖果第j次品尝的价值是v(i)*w(j).q次询问一条链上每个点价值的 ...
- BZOJ3052: [wc2013]糖果公园【树上带修莫队】
Description Input Output Sample Input Sample Input Sample Output 84 131 27 84 HINT 思路 非常模板的树上带修莫队 真的 ...
随机推荐
- BZOJ 4128: Matrix
BZOJ 4128: Matrix 标签(空格分隔): OI BZOJ 大步小步 矩阵 费马小定理 Time Limit: 10 Sec Memory Limit: 128 MB Descriptio ...
- Bootstrap 历练实例-轮播(carousel)插件方法
方法 下面是一些轮播(Carousel)插件中有用的方法: 方法 描述 实例 .carousel(options) 初始化轮播为可选的 options 对象,并开始循环项目. $('#identifi ...
- 操作系统(4)_进程同步_李善平ppt
生产者进程count++是它的临界区,消费者count--是它的临界区. 经典同步问题,死锁问题,略.
- C#冒泡排序程序
考虑到很多面试可能会考察冒泡排序的用法,所以特地花时间厘清了一下思路.下面说一下我的思路:冒泡排序核心就是比较方法,冒泡排序的比较方法顾名思义就是像气泡一样,最大(或者最小)的数往上冒.普通比较几个数 ...
- 【luogu题解】P1546 最短网络 Agri-Net
题目 约翰已经给他的农场安排了一条高速的网络线路,他想把这条线路共享给其他农场.为了用最小的消费,他想铺设最短的光纤去连接所有的农场. 你将得到一份各农场之间连接费用的列表,你必须找出能连接所有农场并 ...
- cf492E. Vanya and Field(扩展欧几里得)
题意 $n \times n$的网格,有$m$个苹果树,选择一个点出发,每次增加一个偏移量$(dx, dy)$,最大化经过的苹果树的数量 Sol 上面那个互素一开始没看见,然后就GG了 很显然,若$n ...
- 抽屉head部分,hover应用,鼠标放上变色
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...
- 两个list缩进为一个list,python
# w_list = ['a', 'b', 'c', 'd'] # e_list = ['c', 'd', 'b', 'a'] w_list = ['a', 'b', 'c', 'd', 'ff', ...
- 二十、Mysql 连接的使用
Mysql 连接的使用 在前几章节中,我们已经学会了如何在一张表中读取数据,这是相对简单的,但是在真正的应用中经常需要从多个数据表中读取数据. 本章节我们将向大家介绍如何使用 MySQL 的 JOIN ...
- hive数据的导入导出方式
导入方式 1.load方式 load data local inpath 'local_path' into table tb_name; 从本地复制了文件到表的路径下 应用场景:大部分的使用,文件几 ...