题目:https://www.lydsy.com/JudgeOnline/problem.php?id=4196

树链剖分。

代码如下:

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
int const maxn=1e5+;
int n,m,fa[maxn],dfn[maxn],end[maxn],top[maxn],to[maxn],siz[maxn],head[maxn],ct,tim;
struct N{
int to,next;
N(int t=,int n=):to(t),next(n) {}
}edge[maxn];
struct T{int sum,siz; bool f[];}t[maxn<<];
int rd()
{
int ret=;char ch=getchar();
while(ch<''||ch>'')ch=getchar();
while(ch>=''&&ch<='')ret=ret*+ch-'',ch=getchar();
return ret;
}
void dfs(int x)
{
siz[x]=;
for(int i=head[x],u;i;i=edge[i].next)
{
dfs(u=edge[i].to);
if(siz[u]>siz[to[x]])to[x]=u;
siz[x]+=siz[u];
}
}
void dfs2(int x)
{
dfn[x]=++tim;//不在dfs
if(to[x])top[to[x]]=top[x],dfs2(to[x]);
for(int i=head[x],u;i;i=edge[i].next)
{
if((u=edge[i].to)==to[x])continue;
top[u]=u; dfs2(u);
}
end[x]=tim;
}
void pushup(int x)
{
int ls=(x<<),rs=(x<<|);
t[x].siz=t[ls].siz+t[rs].siz;
t[x].sum=t[ls].sum+t[rs].sum;
}
void pushdown(int x)
{
if(!t[x].f[]&&!t[x].f[])return;
int ls=(x<<),rs=(x<<|);
for(int i=;i<=;i++)
if(t[x].f[i])
{
t[x].f[i]=; t[ls].f[i]=; t[rs].f[i]=;
t[ls].f[!i]=; t[rs].f[!i]=;
t[ls].sum=t[ls].siz*i; t[rs].sum=t[rs].siz*i;
}
}
void build(int x,int l,int r)
{
if(l==r){t[x].siz=;return;}
int mid=((l+r)>>);
build(x<<,l,mid); build(x<<|,mid+,r);
pushup(x);
}
int query(int x,int l,int r,int L,int R,int val)
{
if(l>=L&&r<=R)
{
if(val)return t[x].sum;
else return t[x].siz-t[x].sum;
}
int mid=((l+r)>>),ret=;
pushdown(x);
if(mid>=L)ret+=query(x<<,l,mid,L,R,val);
if(mid<R)ret+=query(x<<|,mid+,r,L,R,val);
return ret;
}
void update(int x,int l,int r,int L,int R,int val)
{
if(l>=L&&r<=R)
{
t[x].f[val]=; t[x].f[!val]=;
t[x].sum=t[x].siz*val; return;
}
int mid=((l+r)>>);
if(mid>=L)update(x<<,l,mid,L,R,val);
if(mid<R)update(x<<|,mid+,r,L,R,val);
pushup(x);
}
int ask(int x)
{
int ret=;
while(x)
{
int l=dfn[top[x]],r=dfn[x];
ret+=query(,,n,l,r,);
update(,,n,l,r,);
x=fa[top[x]];
}
return ret;
}
int main()
{
n=rd();
for(int i=;i<=n;i++)
{
fa[i]=rd()+;
edge[++ct]=N(i,head[fa[i]]);head[fa[i]]=ct;
}
dfs(); top[]=; dfs2(); build(,,n);
m=rd(); char ch[];
for(int i=,x;i<=m;i++)
{
scanf("%s",&ch); x=rd()+;
if(ch[]=='u')
{
printf("%d\n",query(,,n,dfn[x],end[x],));
update(,,n,dfn[x],end[x],);
}
if(ch[]=='i')
{
printf("%d\n",ask(x));
}
}
return ;
}

bzoj4196 [Noi2015]软件包管理器——树链剖分的更多相关文章

  1. [BZOJ4196][NOI2015]软件包管理器(树链剖分)

    4196: [Noi2015]软件包管理器 Time Limit: 10 Sec  Memory Limit: 512 MBSubmit: 2166  Solved: 1253[Submit][Sta ...

  2. BZOJ4196[Noi2015]软件包管理器——树链剖分+线段树

    题目描述 Linux用户和OSX用户一定对软件包管理器不会陌生.通过软件包管理器,你可以通过一行命令安装某一个软件包,然后软件包管理器会帮助你从软件源下载软件包,同时自动解决所有的依赖(即下载安装这个 ...

  3. [Bzoj4196] [NOI2015] 软件包管理器 [树链剖分,线段树]

    题解摘要:树链剖分后用线段树区间查询修改,对于安装软件,将改点到根的路径全部变为1,对于卸载软件,将子树清空.注意边界,编号是从0开始的,容易漏掉树根. 第一次写树剖- #include <io ...

  4. bzoj4196 [Noi2015]软件包管理器 树链剖分+线段树

    先把树剖分了(又是dfs1.dfs2),然后区间求和.区间覆盖即可 难得的1A好(shui)题 ——写了那么多题,终于有一道是1A的了,加上上一次连续交了几遍A的程序,我的状态莫名好看啊233 总结: ...

  5. 【BZOJ4196】[Noi2015]软件包管理器 树链剖分

    [Noi2015]软件包管理器 树链剖分 Description Linux用户和OSX用户一定对软件包管理器不会陌生.通过软件包管理器,你可以通过一行命令安装某一个软件包,然后软件包管理器会帮助你从 ...

  6. BZOJ 4196: [Noi2015]软件包管理器 [树链剖分 DFS序]

    4196: [Noi2015]软件包管理器 Time Limit: 10 Sec  Memory Limit: 512 MBSubmit: 1352  Solved: 780[Submit][Stat ...

  7. Bzoj 4196: [Noi2015]软件包管理器 树链剖分

    4196: [Noi2015]软件包管理器 Time Limit: 10 Sec  Memory Limit: 512 MBSubmit: 721  Solved: 419[Submit][Statu ...

  8. bzoj 4196 [Noi2015]软件包管理器 (树链剖分+线段树)

    4196: [Noi2015]软件包管理器 Time Limit: 10 Sec  Memory Limit: 512 MBSubmit: 2852  Solved: 1668[Submit][Sta ...

  9. 洛谷 P2146 [NOI2015]软件包管理器 树链剖分

    目录 题面 题目链接 题目描述 输入输出格式 输入格式: 输出格式: 输入输出样例 输入样例#1: 输出样例#1: 输入样例#2: 输出样例#2: 说明 说明 思路 AC代码 总结 题面 题目链接 P ...

随机推荐

  1. 日志不得应用情况切换强制standby改变状态为primary

    日志不得应用情况切换备库为主库 备库运行如下: alter database recover managed standby database disconnect from session; alt ...

  2. bzoj 2337 高斯消元+概率DP

    题目大意: 每条路径上有一个距离值,从1走到N可以得到一个所有经过路径的异或和,求这个异或和的数学期望 这道题直接去求数学期望的DP会导致很难列出多元方程组 我们可以考虑每一个二进制位从1走到N的平均 ...

  3. Lucene的例子

    lucene爬数据库中的数据无非也是查询数据.所有我们用lucene搜索数据主要有下面几个步骤:(代码紧供参考)       一  ,  从数据库中查数据 ====爬数据  ------------- ...

  4. Flex里监听mouseDownOutside事件解决弹出窗口点击空白关闭功能

    其实当用户在使用 PopUpManager 打开的某个组件外部单击时,会从该组件分派一个mouseDownOutside事件 监听该事件就能实现点击空白处关闭窗口的功能 this.addEventLi ...

  5. wordpress优化:Gravatar头像被墙及解决方案

    网站缓存现象: 打开网站是左下角出现0.gravatar.com.1.gravatar.com或2.gravatar.com字样,网站一直处于缓存状态,迟迟未能打开.很多人都会缺乏耐心地等待一个网页的 ...

  6. python学习之-- redis模块操作 集合和有序集合

    redis 模块操作之 集合set和有序集合zset Set 集合操作,不允许重复的列表sadd(name,value):name对应的集合中添加元素scard(name):获取name对应的集合中元 ...

  7. hdu6212 祖玛(区间DP)

    题意 有一个长度为n的01串,我们可以在某个地方插入一个0或者1,那么如果有连续颜色相同的>=3个,那么这段就会消去,两边的合拢.问将所有01串消去,最少需要插入多少个.(n<=200) ...

  8. Unity从实践中学习(1)

    首先在实际中unity的开发之中快捷键应该是相当重要的一个部分,这里先引用csdn的一个博客,https://blog.csdn.net/qq_34552886/article/details/697 ...

  9. linux命名详解及其软件安装实例

    始于cd,ls命令 好啦,步入正题,我使用的linux连接工具为xshell,mRemoteNG,对两款工具不做介绍啦,你可以百度一下,实在不会入左上方群. 进入之后,便是上面的界面黑乎乎一片,对于初 ...

  10. jq自定义裁剪,代码超级简单,易修改

    1.自定义宽高效果 1.html 代码  index.html <!DOCTYPE html> <html lang="en"> <head> ...