题目链接:http://codeforces.com/contest/877/problem/E

题解:显然一看就感觉要么树链剖分要么线段树+dfs序,题目要求的操作显然用线段树+dfs序就可以实现。然后就敲一下线段树+dfs序就行挺简单的只要dfs一遍记录当前节点的下表然后再加一个leng数组来存子树最多到达几然后更新或者求值的时候只要查询(pos[x],leng[x])即可。

#include <iostream>
#include <cstring>
#include <cstdio>
#include <vector>
#define lson (i << 1)
#define rson ((i << 1) | 1)
using namespace std;
const int M = 2e5 + ;
int a[M] , pos[M] , leng[M] , pre[M] , cnt;
vector<int> vc[M];
struct TnT {
int l , r , sum , lazy;
}T[M << ];
void push_up(int i) {
T[i].sum = T[lson].sum + T[rson].sum;
}
void push_down(int i) {
if(T[i].lazy) {
T[lson].sum = T[lson].r - T[lson].l + - T[lson].sum;
T[rson].sum = T[rson].r - T[rson].l + - T[rson].sum;
T[lson].lazy ^= ;
T[rson].lazy ^= ;
T[i].lazy = ;
}
}
void build(int l , int r , int i) {
int mid = (l + r) >> ;
T[i].l = l , T[i].r = r , T[i].sum = , T[i].lazy = ;
if(l == r) {
T[i].sum = a[pre[l]];
return ;
}
push_down(i);
build(l , mid , lson);
build(mid + , r , rson);
push_up(i);
}
void update(int l , int r , int i) {
int mid = (T[i].l + T[i].r) >> ;
if(T[i].l == l && T[i].r == r) {
T[i].sum = (T[i].r - T[i].l + ) - T[i].sum;
T[i].lazy ^= ;
return ;
}
push_down(i);
if(mid < l) {
update(l , r , rson);
}
else if(mid >= r) {
update(l , r , lson);
}
else {
update(l , mid , lson) , update(mid + , r , rson);
}
push_up(i);
}
int query(int l , int r , int i) {
int mid = (T[i].l + T[i].r) >> ;
if(T[i].l == l && T[i].r == r) {
return T[i].sum;
}
push_down(i);
if(mid < l) {
return query(l , r , rson);
}
else if(mid >= r) {
return query(l , r , lson);
}
else {
return query(l , mid , lson) + query(mid + , r , rson);
}
}
void dfs(int u) {
int len = vc[u].size();
for(int i = ; i < len ; i++) {
int v = vc[u][i];
pos[v] = ++cnt;
pre[cnt] = v;
dfs(v);
leng[v] = cnt;
}
}
int main() {
int n , x , q;
char s[];
scanf("%d" , &n);
for(int i = ; i <= n ; i++) {
scanf("%d" , &x);
vc[x].push_back(i);
}
for(int i = ; i <= n ; i++) {
scanf("%d" , &a[i]);
}
scanf("%d" , &q);
cnt = ;
pos[] = ++cnt;
pre[cnt] = ;
leng[] = n;
dfs();
build( , n , );
while(q--) {
scanf("%s" , s);
if(s[] == 'g') {
scanf("%d" , &x);
printf("%d\n" , query(pos[x] , leng[x] , ));
}
else {
scanf("%d" , &x);
update(pos[x] , leng[x] , );
}
}
return ;
}

codeforces 877 E. Danil and a Part-time Job(线段树(dfs序))的更多相关文章

  1. Codeforces 571D - Campus(并查集+线段树+DFS 序,hot tea)

    Codeforces 题目传送门 & 洛谷题目传送门 看到集合的合并,可以本能地想到并查集. 不过这题的操作与传统意义上的并查集不太一样,传统意义上的并查集一般是用来判断连通性的,而此题还需支 ...

  2. Codeforces 877E - Danil and a Part-time Job 线段树+dfs序

    给一个有根树,1e5个节点,每个节点有权值0/.1,1e5操作:1.将一个点的子树上所有点权值取反2.查询一个点的子树的权值和   题解: 先深搜整颗树,用dfs序建立每个点对应的区间,等于把树拍扁成 ...

  3. Codeforces 343D WaterTree - 线段树, DFS序

    Description Translated by @Nishikino_Maki from Luogu 行吧是我翻的 Mad scientist Mike has constructed a roo ...

  4. Codeforces Round #620 F2. Animal Observation (hard version) (dp + 线段树)

    Codeforces Round #620 F2. Animal Observation (hard version) (dp + 线段树) 题目链接 题意 给定一个nm的矩阵,每行取2k的矩阵,求总 ...

  5. Codeforces Round #292 (Div. 1) C. Drazil and Park 线段树

    C. Drazil and Park 题目连接: http://codeforces.com/contest/516/problem/C Description Drazil is a monkey. ...

  6. Codeforces Round #254 (Div. 1) C. DZY Loves Colors 线段树

    题目链接: http://codeforces.com/problemset/problem/444/C J. DZY Loves Colors time limit per test:2 secon ...

  7. Codeforces Round #337 (Div. 2) D. Vika and Segments 线段树扫描线

    D. Vika and Segments 题目连接: http://www.codeforces.com/contest/610/problem/D Description Vika has an i ...

  8. Codeforces Round #337 (Div. 2) D. Vika and Segments (线段树+扫描线+离散化)

    题目链接:http://codeforces.com/contest/610/problem/D 就是给你宽度为1的n个线段,然你求总共有多少单位的长度. 相当于用线段树求面积并,只不过宽为1,注意y ...

  9. Codeforces Round #149 (Div. 2) E. XOR on Segment (线段树成段更新+二进制)

    题目链接:http://codeforces.com/problemset/problem/242/E 给你n个数,m个操作,操作1是查询l到r之间的和,操作2是将l到r之间的每个数xor与x. 这题 ...

随机推荐

  1. Asp.Net MVC 高级特性(附带源码剖析)

    1. 程序入口(MvcHandler,RouteHandler,HttpModule) 2.异步类包(静态类AsyncResultWrapper),开启整个MVC异步循环 3.Aggregate递归链 ...

  2. oracle的JDBC连接

    package com.xian.jdbc; import java.sql.Connection; import java.sql.DriverManager; import java.sql.Pr ...

  3. Hadoop 系列(二)—— 集群资源管理器 YARN

    一.hadoop yarn 简介 Apache YARN (Yet Another Resource Negotiator) 是 hadoop 2.0 引入的集群资源管理系统.用户可以将各种服务框架部 ...

  4. Android 属性动画实战

    什么是属性动画? 属性动画可以通过直接更改 View 的属性来实现 View 动画.例如: 通过不断的更改 View 的坐标来实现让 View 移动的效果: 通过不断的更改 View 的背景来实现让 ...

  5. 10、二维数组的申请(test7.java)

    我个人认为,二维数组的构造就是在一位数组中存入一个地址,这个地址指向另一个一位数组,这样通过这种排列组合便构造成了二维数组. 二维数组的形状,有的时候二维数组看起来像是一个矩阵,所以一般情况下如果涉及 ...

  6. 【POJ - 3176】牛保龄球 (简单dp)

    牛保龄球 直接中文了 Descriptions 奶牛打保龄球时不使用实际的保龄球.它们各自取一个数字(在0..99范围内),然后排成一个标准的保龄球状三角形,如下所示: 7 3 8 8 1 0 2 7 ...

  7. 两个 github 账号混用,一个帐号提交错误

    问题是这样,之前有一个github帐号,因为注册邮箱的原因,不打算继续使用了,换了一个新的邮箱注册了一个新的邮箱帐号.新账号提交 就会出现下图的问题,但是原来帐号的库还是能正常提交.   方法1:添加 ...

  8. mysql优化---订单查询优化(2):异步分页处理

    订单分页查询: 老的代码是顺序执行查询数据和计算总记录数,但是如果条件复杂的话(比如关联子表)查询的时间要超过20s种 public static PagedList<Map<String ...

  9. Vue 中使用 typescript

    Vue 中使用 typescript 什么是typescript typescript 为 javaScript的超集,这意味着它支持所有都JavaScript都语法.它很像JavaScript都强类 ...

  10. 洛谷 P5367 【模板】康托展开(数论,树状数组)

    题目链接 https://www.luogu.org/problem/P5367 什么是康托展开 百度百科上是这样说的:   “康托展开是一个全排列到一个自然数的双射,常用于构建哈希表时的空间压缩. ...