俩操作:增加路径上的点的权值。查询子树的权值和。

  想了想似乎只能树链剖分了。。好久没写链剖+数据结构了TAT

  一开始没开LL炸了一发(明明有想到的。。我果然是傻逼= =

 #include<cstdio>
#include<iostream>
#include<cstring>
#include<algorithm>
#define ll long long
using namespace std;
const int maxn=;
struct zs{
int too,pre;
}e[maxn<<];int tot,last[maxn];
int lc[maxn<<],rc[maxn<<],tt;
ll sm[maxn<<],tag[maxn<<];
int dfn[maxn],sz[maxn],fa[maxn],top[maxn],dep[maxn],tim;
int i,j,k,n,m,x,y,lca,v; int ra;char rx;
inline int read(){
rx=getchar(),ra=;
while(rx<''||rx>'')rx=getchar();
while(rx>=''&&rx<='')ra*=,ra+=rx-,rx=getchar();return ra;
} inline void dfs1(int x){
sz[x]=,dep[x]=dep[fa[x]]+;
for(int i=last[x];i;i=e[i].pre)
dfs1(e[i].too),sz[x]+=sz[e[i].too];
}
inline void dfs2(int x,int chain){
top[x]=chain,dfn[x]=++tim;int i,mx=;
for(i=last[x];i;i=e[i].pre)if(sz[e[i].too]>sz[mx])mx=e[i].too;
if(!mx)return;
dfs2(mx,chain);
for(i=last[x];i;i=e[i].pre)if(e[i].too!=mx)dfs2(e[i].too,e[i].too);
}
inline int getlca(int a,int b){
while(top[a]!=top[b]){
if(dep[top[a]]<dep[top[b]])swap(a,b);
a=fa[top[a]];
}
return dep[a]<dep[b]?a:b;
} inline void insert(int a,int b){e[++tot].too=b,e[tot].pre=last[a],last[a]=tot;} inline void pushdown(int x,int a,int b,int mid,int lc,int rc){
tag[lc]+=tag[x],tag[rc]+=tag[x],sm[lc]+=tag[x]*(mid-a+),sm[rc]+=tag[x]*(b-mid);
tag[x]=;
}
#define upd(x) sm[x]=sm[lc[x]]+sm[rc[x]];
inline void add(int x,int a,int b,int l,int r,int v){
// printf("add:%d %d %d %d--%d %d\n",x,a,b,l,r,v);
if(l<=a&&r>=b){tag[x]+=v,sm[x]+=(ll)(b-a+)*v;/*,printf("! %d\n",sm[x]);*/return;}
int mid=(a+b)>>;
if(tag[x])pushdown(x,a,b,mid,lc[x],rc[x]);
if(l<=mid)add(lc[x],a,mid,l,r,v);
if(r>mid) add(rc[x],mid+,b,l,r,v);
upd(x);//printf(" %d--%d %d %d %d\n",a,b,sm[x],sm[lc[x]],sm[rc[x]]);
}
inline ll query(int x,int a,int b,int l,int r){
if(l<=a&&r>=b)return sm[x];
int mid=(a+b)>>;
if(tag[x])pushdown(x,a,b,mid,lc[x],rc[x]);
if(r<=mid)return query(lc[x],a,mid,l,r);else
if(l>mid)return query(rc[x],mid+,b,l,r);else
return query(lc[x],a,mid,l,r)+query(rc[x],mid+,b,l,r);
}
inline void build(int a,int b){
tt++;
if(a==b)return;
int mid=(a+b)>>,x=tt;
lc[x]=tt+,build(a,mid),rc[x]=tt+,build(mid+,b);
} inline void ADD(int x,int y,int v){
while(top[x]!=top[y]){
add(,,n,dfn[top[x]],dfn[x],v);
x=fa[top[x]];
}
add(,,n,dfn[y],dfn[x],v);
}
/*inline ll QUERY(int x,int y){
ll sum=0;
while(top[x]!=top[y]){
sum+=query(1,1,n,dfn[top[x]],dfn[x]);
x=fa[top[x]];
}
return sum+query(1,1,n,dfn[y],dfn[x]);
}*/ int main(){
n=read();
for(i=;i<n;i++)x=read()+,y=read()+,fa[y]=x,insert(x,y);
dfs1(),dfs2(,);
build(,n);char id;
for(m=read();m;m--){
for(id=getchar();id<'A'||id>'Z';id=getchar());
if(id=='A'){
x=read()+,y=read()+,v=read(),
lca=getlca(x,y);//printf(" %d %d lca:%d\n",x,y,lca);
ADD(x,lca,v),ADD(y,lca,v),add(,,n,dfn[lca],dfn[lca],-v);
}else{
x=read()+;
//ll sum=QUERY(x,lca)+QUERY(y,lca)-query(1,1,n,dfn[lca],dfn[lca]);
ll sum=query(,,n,dfn[x],dfn[x]+sz[x]-);
printf("%lld\n",sum);
}
}
return ;
}

[bzoj2836] 魔法树的更多相关文章

  1. 【树链剖分】【dfs序】【线段树】bzoj2836 魔法树

    这道题告诉我们:树链剖分的重标号就是dfs序. #include<cstdio> #include<algorithm> using namespace std; #defin ...

  2. noip模拟赛(一)魔法树

    魔法树 (mahou.pas/c/cpp) [问题描述] 魔法使moreD在研究一棵魔法树. 魔法树顾名思义,这货是一棵树,奇葩的是魔法树上的每一条边都拥有一个魔法属性,如果不那么奇葩就不是moreD ...

  3. P3833 [SHOI2012]魔法树

    思路 树剖板子 注意给出点的编号是从零开始的 代码 #include <cstdio> #include <algorithm> #include <cstring> ...

  4. [洛谷P3833][SHOI2012]魔法树

    题目大意:给一棵树,路径加,子树求和 题解:树剖 卡点:无 C++ Code: #include <cstdio> #include <iostream> #define ma ...

  5. 树链剖分【洛谷P3833】 [SHOI2012]魔法树

    P3833 [SHOI2012]魔法树 题目描述 Harry Potter 新学了一种魔法:可以让改变树上的果子个数.满心欢喜的他找到了一个巨大的果树,来试验他的新法术. 这棵果树共有N个节点,其中节 ...

  6. 树链剖分【P3833】 [SHOI2012]魔法树

    Description Harry Potter 新学了一种魔法:可以让改变树上的果子个数.满心欢喜的他找到了一个巨大的果树,来试验他的新法术. 这棵果树共有N个节点,其中节点0是根节点,每个节点u的 ...

  7. [SHOI 2012] 魔法树

    [题目链接] https://www.lydsy.com/JudgeOnline/problem.php?id=2836 [算法] 树链剖分 时间复杂度 : O(NlogN ^ 2) [代码] #in ...

  8. 洛谷 3833 SHOI 2012 魔法树

    [题解] 树链剖分模板题.. #include<cstdio> #include<algorithm> #include<queue> #define N 5000 ...

  9. 洛谷——P3833 [SHOI2012]魔法树

    P3833 [SHOI2012]魔法树 题目背景 SHOI2012 D2T3 题目描述 Harry Potter 新学了一种魔法:可以让改变树上的果子个数.满心欢喜的他找到了一个巨大的果树,来试验他的 ...

随机推荐

  1. Hibernate学习---基本介绍+作用+配置

    从今天开始重新学习(以前学的太匆忙)Hibernate,这篇文章主要就一下几点进行讲解和说明: Hibernate的基本介绍 Hibernate的作用 Hibernate基本配置 Hibernate的 ...

  2. iOS 面试题、知识点 之一

    最近面试,发现这些题个人遇到的几率大一些,与大家分享一下,分三文给大家: 当然Xcode新版本与之前一版本的区别,以及iOS新特性是必要了解的吧. Xcode8 和iOS 10 在之前文章有发过,感兴 ...

  3. crm踩坑记(三)

    React 如何同步更新state 由于setState方法是异步的,而通常很多时候在一个生命周期里更新state后需要在另一个生命周期里使用这个state. 下面介绍几个方法 // 1 this.s ...

  4. ActiveMQ (一) 初识ActiveMQ

    了解JMS JMS即Java消息服务(Java Message Service)应用程序接口是一个Java平台中关于面向消息中间件(MOM)的API,用于在两个应用程序之间,或分布式系统中发送消息,进 ...

  5. Apache Avro# 1.8.2 Specification (Avro 1.8.2规范)一

    h4 { text-indent: 0.71cm; margin-top: 0.49cm; margin-bottom: 0.51cm; direction: ltr; color: #000000; ...

  6. gitlab 本地 定时备份

    =============================================== 20171015_第1次修改                       ccb_warlock === ...

  7. touch监听判断手指的上滑,下滑,左滑,右滑,事件监听

    判断滑动的方向和距离,来实现一定的效果,比如返回上一页等等 <body> <script> $(function(){ //给body强制定义高度 var windowHeig ...

  8. python如何进行内存管理

    作者:Vamei 出处:http://www.cnblogs.com/vamei 欢迎转载,也请保留这段声明.谢谢! 语言的内存管理是语言设计的一个重要方面.它是决定语言性能的重要因素.无论是C语言的 ...

  9. 消息队列一:为什么需要消息队列(MQ)?

    为什么会需要消息队列(MQ)? #################################################################################### ...

  10. iOS学习——UI相关小结

    1     StoryBoard: 在Info.plist中可以查看Main storyboard,即入口storyboard,默认为main.storyboard,可以修改为自己创建的storybo ...