【NOI 2015】软件包管理器
【算法】
树链剖分,子树的DFS序也是连续的一段
要注意细节!
【代码】
#include<bits/stdc++.h>
using namespace std;
#define MAXN 100000 struct SegmentTree {
int l,r,sum[],opt;
} tree[MAXN*]; int i,N,Q,x,num;
int depth[MAXN+],size[MAXN+],son[MAXN+],fa[MAXN+],
top[MAXN+],id[MAXN+];
string type;
vector<int> E[MAXN+]; template <typename T> inline void read(T &x) {
int f = ; x = ;
char c = getchar();
for (; !isdigit(c); c = getchar()) { if (c == '-') f = -f; }
for (; isdigit(c); c = getchar()) x = x * + c - '';
x *= f;
} template <typename T> inline void write(T x) {
if (x < ) { putchar('-'); x = -x; }
if (x > ) write(x/);
putchar(x%+'');
} template <typename T> inline void writeln(T x) {
write(x);
puts("");
} inline void dfs1(int x) {
int i,y;
size[x] = ;
for (i = ; i < E[x].size(); i++) {
y = E[x][i];
if (y != fa[x]) {
fa[y] = x;
depth[y] = depth[x] + ;
dfs1(y);
size[x] += size[y];
if ((size[y] > size[son[x]]) || (!son[x])) son[x] = y;
}
}
} inline void dfs2(int x,int tp) {
int i,y;
top[x] = tp; id[x] = ++num;
if (son[x]) dfs2(son[x],tp);
for (i = ; i < E[x].size(); i++) {
y = E[x][i];
if ((y != fa[x]) && (y != son[x]))
dfs2(y,y);
}
} inline void build(int index,int l,int r) {
int mid;
tree[index].l = l; tree[index].r = r;
tree[index].opt = ;
tree[index].sum[] = r - l + ;
if (l == r) return;
mid = (l + r) >> ;
build(index*,l,mid); build(index*+,mid+,r);
} inline void pushdown(int index) {
if (tree[index].l == tree[index].r) return;
tree[index*].opt = tree[index].opt;
tree[index*].sum[tree[index].opt] = tree[index*].r - tree[index*].l + ;
tree[index*].sum[tree[index].opt^] = ;
tree[index*+].opt = tree[index].opt;
tree[index*+].sum[tree[index].opt] = tree[index*+].r - tree[index*+].l + ;
tree[index*+].sum[tree[index].opt^] = ;
} inline void pushup(int index) {
tree[index].sum[] = tree[index*].sum[] + tree[index*+].sum[];
tree[index].sum[] = tree[index*].sum[] + tree[index*+].sum[];
if (tree[index*].opt != tree[index*+].opt) {
tree[index].opt = -;
return;
}
if ((tree[index*].opt == -) || (tree[index*+].opt == -)) {
tree[index].opt = -;
return;
}
tree[index].opt = tree[index*].opt;
} void modify(int index,int l,int r,int val) {
int mid;
if (tree[index].opt != -) pushdown(index);
if ((tree[index].l == l) && (tree[index].r == r)) {
tree[index].sum[val] = r - l + ;
tree[index].sum[val^] = ;
tree[index].opt = val;
} else {
mid = (tree[index].l + tree[index].r) >> ;
if (mid >= r) modify(index*,l,r,val);
else if (mid + <= l) modify(index*+,l,r,val);
else {
modify(index*,l,mid,val);
modify(index*+,mid+,r,val);
}
pushup(index);
}
} inline int query(int index,int l,int r,int val) {
int mid;
if (tree[index].opt != -) pushdown(index);
if ((tree[index].l == l) && (tree[index].r == r)) return tree[index].sum[val];
else {
mid = (tree[index].l + tree[index].r) >> ;
if (mid >= r) return query(index*,l,r,val);
else if (mid + <= l) return query(index*+,l,r,val);
else return query(index*,l,mid,val) + query(index*+,mid+,r,val);
}
} inline int Install(int x) {
int tp = top[x],
ans = ;
while (tp) {
ans += query(,id[tp],id[x],);
modify(,id[tp],id[x],);
x = fa[tp]; tp = top[x];
}
ans += query(,,id[x],);
modify(,,id[x],);
return ans;
} inline int Uninstall(int x) {
int ans = query(,id[x],id[x]+size[x]-,);
modify(,id[x],id[x]+size[x]-,);
return ans;
} int main() { read(N); for (i = ; i < N; i++) {
read(x);
E[x].push_back(i);
} depth[] = ;
dfs1();
dfs2(,); build(,,num); read(Q);
while (Q--) {
cin >> type;
if (type == "install") {
read(x);
writeln(Install(x));
} else {
read(x);
writeln(Uninstall(x));
}
} return ;
}
【NOI 2015】软件包管理器的更多相关文章
- [NOI 2015]软件包管理器
Description Linux用户和OSX用户一定对软件包管理器不会陌生. 通过软件包管理器,你可以通过一行命令安装某一个软件包,然后软件包管理器会帮助你从软件源下载软件包,同时自动解决所有的依赖 ...
- [bzoj 4196][NOI 2015]软件包管理器
大概算是一道模板题吧? 就是细节有点多 罗列一下: 如果习惯从1开始搞树的编号的话,处理输入进来的那个依赖关系在加边的时候两个都要+1,体现在代码就是i要从2枚举到n,然后输入进来的那个数要+1 这道 ...
- BZOJ4196 软件包管理器
Description Linux用户和OSX用户一定对软件包管理器不会陌生. 通过软件包管理器,你可以通过一行命令安装某一个软件包,然后软件包管理器会帮助你从软件源下载软件包,同时自动解决所有的依赖 ...
- 【NOI2015】软件包管理器
NOI难得的水题,话说还是T2诶……又学到了线段树的一种新的魔性使用 看sxysxy大神的代码才写出来的,sxysxy_orz 原题: Linux用户和OSX用户一定对软件包管理器不会陌生.通过软件包 ...
- BZOJ4196 [Noi2015]软件包管理器 【树剖】
题目 Linux用户和OSX用户一定对软件包管理器不会陌生.通过软件包管理器,你可以通过一行命令安装某一个软件包,然后软件包管理器会帮助你从软件源下载软件包,同时自动解决所有的依赖(即下载安装这个软件 ...
- [bzoj4196][Noi2015]软件包管理器_树链剖分_线段树
软件包管理器 bzoj-4196 Noi-2015 题目大意:Linux用户和OSX用户一定对软件包管理器不会陌生.通过软件包管理器,你可以通过一行命令安装某一个软件包,然后软件包管理器会帮助你从软件 ...
- BZOJ 4196: [Noi2015]软件包管理器 [树链剖分 DFS序]
4196: [Noi2015]软件包管理器 Time Limit: 10 Sec Memory Limit: 512 MBSubmit: 1352 Solved: 780[Submit][Stat ...
- [BZOJ4196][NOI2015]软件包管理器
4196: [Noi2015]软件包管理器 Time Limit: 10 Sec Memory Limit: 512 MBSubmit: 1040 Solved: 603[Submit][Stat ...
- Mac 系统下类似于 apt-get 的软件包管理器 -- Homebrew
对于一个习惯了在 Ubuntu 的终端上通过 apt-get 来安装工具软件的我来说,也希望在Mac上找到类似的工具,能很方便的一条命令就能安装所需的软件,而不用手工的去查找下载编译,或者是折腾安装所 ...
- Chocolatey:Windows软件包管理器
Chocolatey 2016-08-03 https://chocolatey.org/ Chocolatey是一个Windows软件包管理器,就像Nuget或者npm,或者说类似Linux上的ap ...
随机推荐
- js创建post请求
/**js提交post请求:隐藏请求参数**/function postDetail(URL, PARAMTERS) { //创建form表单 var temp_form = document.cre ...
- 如何在ASP.NET Core自定义中间件中读取Request.Body和Response.Body的内容?
原文:如何在ASP.NET Core自定义中间件中读取Request.Body和Response.Body的内容? 文章名称: 如何在ASP.NET Core自定义中间件读取Request.Body和 ...
- LVM创建
LVM介绍 PV(Physical Volume) - 物理卷 物理卷在逻辑卷管理中处于最底层,它可以是实际物理硬盘上的分区,也可以是整个物理硬盘,也可以是raid设备 VG(Volume Group ...
- Java基础 笔记(四)
泛型: 泛型:通过<数据额类型>来接受一种引用数据类型.作用在编译时.使用检查 加入集合的对象是否属于该类型,从而把执行时的问题转换为编译时异常.提高程序的安全性 避免抛出 ClassCa ...
- VS2013带来的"新特性"
VS2013除了引入"Bootstrap"库以外,最大的变化就是.net Framework 4.5下面的都不支持了.也就是说,假设不把.net库升级成.net Framework ...
- eureka高可用注册中心
Eureka高可用注册中心 两个配置文件: application-peer1.properties application-peer2.properties 都需要加上 eureka.client. ...
- testng 工程报错java.net.SocketException
报错如下: java.net.SocketException: Software caused connection abort: socket write error at java.net.Soc ...
- 【Java】Java代码经典错误清单
一.String 对照 == 和 equals.详细描写叙述例如以下 "=="操作符的作用 1)用于基本数据类型的比較,例如以下: byte(字节) 8 -128 - 127 0 ...
- HDU 3639 Hawk-and-Chicken
Hawk-and-Chicken Time Limit: 6000/2000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) ...
- ObjectARX学习笔记(三十二)----怎样设置AcDbMText对齐方式
//_T("\\pxql;") 居左 //_T("\\pxqr;") 居右 //_T("\\pxqc;") 居中 //_T("\\ ...