B20J_2836_魔法树_树链剖分+线段树
B20J_2836_魔法树_树链剖分+线段树
题意:
果树共有N个节点,其中节点0是根节点,每个节点u的父亲记为fa[u]。初始时,这个果树的每个节点上都没有果子(即0个果子)。
Add u v d
表示将点u和v之间的路径上的所有节点的果子个数都加上d。
Query u
表示当前果树中,以点u为根的子树中,总共有多少个果子?
分析:树链剖分+线段树模板题。记录一下x结点的子树中最后一次出现的位置即可。
代码:
#include <stdio.h>
#include <string.h>
#include <algorithm>
using namespace std;
#define N 100010
#define lson pos<<1
#define rson pos<<1|1
#define LL long long
int head[N],to[N<<1],nxt[N<<1],cnt,n,tot,m;
int dep[N],siz[N],fa[N],son[N],idx[N],top[N],sec[N];
LL t[N<<2],lz[N<<2];
char ch[10];
inline void read(int &x)
{
int f=1;x=0;char s=getchar();
while(s<'0'||s>'9'){if(s=='-')f=-1;s=getchar();}
while(s>='0'&&s<='9'){x=(x<<3)+(x<<1)+s-'0';s=getchar();}
x*=f;
}
inline void add(int u,int v)
{
to[++cnt]=v;
nxt[cnt]=head[u];
head[u]=cnt;
}
inline void dfs1(int x,int y)
{
dep[x]=dep[y]+1;
fa[x]=y;
siz[x]=1;
for(int i=head[x];i;i=nxt[i])
{
if(to[i]!=y)
{
dfs1(to[i],x);
siz[to[i]]+=siz[x];
if(siz[to[i]]>siz[son[x]])
{
son[x]=to[i];
}
}
}
}
inline void dfs2(int x,int t)
{
top[x]=t;
idx[x]=++tot;
if(son[x])dfs2(son[x],t);
for(int i=head[x];i;i=nxt[i])
{
if(to[i]!=fa[x]&&to[i]!=son[x])
{
dfs2(to[i],to[i]);
}
}
sec[x]=tot;
}
inline void pud(int l,int r,int pos,int c)
{
t[pos]+=(r-l+1)*c;
lz[pos]+=c;
}
inline void up(int l,int r,int x,int y,int z,int pos)
{
if(x<=l&&y>=r)
{
t[pos]+=(r-l+1)*z;
lz[pos]+=z;
return ;
}
int mid=l+r>>1;
if(lz[pos])
{
pud(l,mid,lson,lz[pos]);
pud(mid+1,r,rson,lz[pos]);
lz[pos]=0;
}
if(x<=mid)up(l,mid,x,y,z,lson);
if(y>mid)up(mid+1,r,x,y,z,rson);
t[pos]=t[lson]+t[rson];
}
inline LL query(int l,int r,int x,int y,int pos)
{
if(x<=l&&y>=r)
{
return t[pos];
}
int mid=l+r>>1;
if(lz[pos])
{
pud(l,mid,lson,lz[pos]);
pud(mid+1,r,rson,lz[pos]);
lz[pos]=0;
}
LL re=0;
if(x<=mid)re+=query(l,mid,x,y,lson);
if(y>mid)re+=query(mid+1,r,x,y,rson);
return re;
}
int main()
{
read(n);
register int x,y,i,z;
for(i=1;i<n;++i)
{
read(x),read(y);
add(x+1,y+1);
add(y+1,x+1);
}
dfs1(1,0);
dfs2(1,1);
read(m);
while(m--)
{
scanf("%s",ch);
if(ch[0]=='A')
{
read(x),read(y),read(z);
x++,y++;
while(top[x]!=top[y])
{
if(dep[top[x]]>dep[top[y]])swap(x,y);
up(1,n,idx[top[y]],idx[y],z,1);
y=fa[top[y]];
}
if(dep[x]<dep[y])swap(x,y);
up(1,n,idx[y],idx[x],z,1);
}
else
{
read(x);
x++;
printf("%lld\n",query(1,n,idx[x],sec[x],1));
}
}
}
B20J_2836_魔法树_树链剖分+线段树的更多相关文章
- B20J_2243_[SDOI2011]染色_树链剖分+线段树
B20J_2243_[SDOI2011]染色_树链剖分+线段树 一下午净调这题了,争取晚上多做几道. 题意: 给定一棵有n个节点的无根树和m个操作,操作有2类: 1.将节点a到节点b路径上所有点都染成 ...
- B20J_3231_[SDOI2014]旅行_树链剖分+线段树
B20J_3231_[SDOI2014]旅行_树链剖分+线段树 题意: S国有N个城市,编号从1到N.城市间用N-1条双向道路连接,城市信仰不同的宗教,为了方便,我们用不同的正整数代表各种宗教. S国 ...
- 【BZOJ-2325】道馆之战 树链剖分 + 线段树
2325: [ZJOI2011]道馆之战 Time Limit: 40 Sec Memory Limit: 256 MBSubmit: 1153 Solved: 421[Submit][Statu ...
- 【BZOJ2243】[SDOI2011]染色 树链剖分+线段树
[BZOJ2243][SDOI2011]染色 Description 给定一棵有n个节点的无根树和m个操作,操作有2类: 1.将节点a到节点b路径上所有点都染成颜色c: 2.询问节点a到节点b路径上的 ...
- BZOJ2243 (树链剖分+线段树)
Problem 染色(BZOJ2243) 题目大意 给定一颗树,每个节点上有一种颜色. 要求支持两种操作: 操作1:将a->b上所有点染成一种颜色. 操作2:询问a->b上的颜色段数量. ...
- POJ3237 (树链剖分+线段树)
Problem Tree (POJ3237) 题目大意 给定一颗树,有边权. 要求支持三种操作: 操作一:更改某条边的权值. 操作二:将某条路径上的边权取反. 操作三:询问某条路径上的最大权值. 解题 ...
- bzoj4034 (树链剖分+线段树)
Problem T2 (bzoj4034 HAOI2015) 题目大意 给定一颗树,1为根节点,要求支持三种操作. 操作 1 :把某个节点 x 的点权增加 a . 操作 2 :把某个节点 x 为根的子 ...
- HDU4897 (树链剖分+线段树)
Problem Little Devil I (HDU4897) 题目大意 给定一棵树,每条边的颜色为黑或白,起始时均为白. 支持3种操作: 操作1:将a->b的路径中的所有边的颜色翻转. 操作 ...
- Aizu 2450 Do use segment tree 树链剖分+线段树
Do use segment tree Time Limit: 1 Sec Memory Limit: 256 MB 题目连接 http://www.bnuoj.com/v3/problem_show ...
随机推荐
- 万水千山ABP - 单租户时,成功保存数据后,数据不显示
问题描述: ABP 禁用了多租户,在编辑一个实体记录后,能成功地保存数据,但数据列表中看不到这条记录.打开数据表查看,发现该实体记录的 TenantId 字段值成了 Null , 而不是预期的默认租户 ...
- 《深入理解Java虚拟机》读书笔记3--垃圾回收算法
转载:http://blog.csdn.net/tjiyu/article/details/53983064 下面先来了解Java虚拟机垃圾回收的几种常见算法:标记-清除算法.复制算法.标记-整理算法 ...
- 修改was数据源
本机的RAD运行的工程可以通过修改jpa中的persistence中的jni修改数据源: 对于通过was控制台部署的ear需要在was控制台:资源--jdbc 修改数据源
- 使用HttpClient进行https连接(一)
一.生成密钥库和证书 1.生成服务器证书库 keytool -validity 365 -genkey -v -alias uyun -keyalg RSA -keystore /opt/UEM/ke ...
- access窗体最大化到软件大小
Private Sub Form_Load()DoCmd.ShowToolbar "Ribbon", acToolbarNo '窗体最大化,占满软件最 End Sub
- JavaScript中对象数组 根据某个属性值 然后push到新的数组
原文链接 https://segmentfault.com/q/1010000010075035 将下列对象数组中,工资大于1w的员工,增加到对象数组 WanSalary中 var BaiduUser ...
- Python-网站页面代码获取
Python3.6 库:urllib3, bs4 主程序是抓取亚马逊图书销售排名数据,但是亚马逊应该是加了反爬虫,拒绝疑似机器人的请求,这部分暂时以百度代替. 其实简单的页面抓取,常用的urllib. ...
- 利用Tess4J实现图片识别
一.下载 1.进入官网下载页面 https://sourceforge.net/projects/tess4j/ 2.点击download 3.下载后解压,目录如下,圈出的三个文件夹是需要用到的 二. ...
- 8人/天,小记一次 JAVA(APP后台) 项目改造 .NET 过程(后台代码已完整开源于 Github)
Github: https://github.com/iccb1013/Jade.Net 我们只消耗了8人/天的时间,完成了全部工作,基于我们 Jade.Net 的开源后台代码,任何小规模的后台管理系 ...
- 一道面试题引发的思考(C#值类型和引用类型)
某年某月,笔者去面试招行的一个外包项目,辗转来到面试地点以后,面试官给了我一份试卷,试卷只有两道题目,其中一道是这样的: 阅读以下程序 class Program { struct Point { p ...