题目链接

题意:

  一棵以1为根的树,树上每个节点有颜色标记(<=60),有两种操作:

  1. 可以把某个节点的子树的节点(包括本身)都改成某种颜色

  2. 查询某个节点的子树上(包括本身)有多少个不同的颜色

思路:

  和2012年多校第7场的G题是同类题,DFS序处理出每个节点管辖的管辖范围[L[u], R[u]],其中L[u]就是子树根节点u所在的位置,用线段树成端更新颜色变化,注意到颜色(<=60),可以用bitset<60>,0表示没有这个颜色,1表示有,异或就能区间合并,最后count一下不同颜色的个数。

另外:

  以前这种题是做不了的,现在都能秒掉了,说明在进步:)

#include <bits/stdc++.h>

const int N = 4e5 + 5;
int a[N];
std::vector<int> edge[N];
int L[N], R[N], id[N];
int tim; #define lson l, mid, o << 1
#define rson mid + 1, r, o << 1 | 1
struct Node {
std::bitset<60> color;
int lazy;
};
Node node[N<<2]; void push_up(int o) {
node[o].color = node[o<<1].color | node[o<<1|1].color;
} void push_down(int o) {
if (node[o].lazy != -1) {
node[o<<1].lazy = node[o<<1|1].lazy = node[o].lazy;
node[o<<1].color.reset ();
node[o<<1].color.set (node[o].lazy);
node[o<<1|1].color.reset ();
node[o<<1|1].color.set (node[o].lazy);
node[o].lazy = -1;
}
} void build(int l, int r, int o) {
node[o].lazy = -1;
node[o].color.reset (); //clear to 0
if (l == r) {
node[o].color.set (a[id[l]]); //set to 1
return ;
}
int mid = l + r >> 1;
build (lson);
build (rson);
push_up (o);
} void updata(int ql, int qr, int c, int l, int r, int o) {
if (ql <= l && r <= qr) {
node[o].lazy = c;
node[o].color.reset ();
node[o].color.set (c);
return ;
}
push_down (o);
int mid = l + r >> 1;
if (ql <= mid) {
updata (ql, qr, c, lson);
}
if (qr > mid) {
updata (ql, qr, c, rson);
}
push_up (o);
} std::bitset<60> query(int ql, int qr, int l, int r, int o) {
if (ql <= l && r <= qr) {
return node[o].color;
}
push_down (o);
int mid = l + r >> 1;
std::bitset<60> ret;
if (ql <= mid) {
ret |= query (ql, qr, lson);
}
if (qr > mid) {
ret |= query (ql, qr, rson);
}
return ret;
} void DFS(int u, int fa) {
L[u] = ++tim; id[tim] = u;
for (auto v: edge[u]) {
if (v != fa) {
DFS (v, u);
}
}
R[u] = tim;
} int main() {
int n, m;
scanf ("%d%d", &n, &m);
for (int i=1; i<=n; ++i) {
scanf ("%d", a+i);
a[i]--;
}
for (int i=1; i<n; ++i) {
int x, y;
scanf ("%d%d", &x, &y);
edge[x].push_back (y);
edge[y].push_back (x);
}
tim = 0;
DFS (1, 0);
build (1, tim, 1); for (int i=0; i<m; ++i) {
int type, v;
scanf ("%d%d", &type, &v);
if (type == 1) {
int c;
scanf ("%d", &c);
c--;
updata (L[v], R[v], c, 1, tim, 1);
} else {
std::bitset<60> ans = query (L[v], R[v], 1, tim, 1);
printf ("%d\n", ans.count ());
}
}
return 0;
}

  

DFS序+线段树+bitset CF 620E New Year Tree(圣诞树)的更多相关文章

  1. Codeforces633G(SummerTrainingDay06-I dfs序+线段树+bitset)

    G. Yash And Trees time limit per test:4 seconds memory limit per test:512 megabytes input:standard i ...

  2. Manthan, Codefest 16 G. Yash And Trees dfs序+线段树+bitset

    G. Yash And Trees 题目连接: http://www.codeforces.com/contest/633/problem/G Description Yash loves playi ...

  3. DFS序+线段树 hihoCoder 1381 Little Y's Tree(树的连通块的直径和)

    题目链接 #1381 : Little Y's Tree 时间限制:24000ms 单点时限:4000ms 内存限制:512MB 描述 小Y有一棵n个节点的树,每条边都有正的边权. 小J有q个询问,每 ...

  4. codeforces 620E. New Year Tree dfs序+线段树+bitset

    题目链接 给一棵树, 每个节点有颜色, 两种操作, 一种是将一个节点的子树全都染色成c, 一种是查询一个节点的子树有多少个不同的颜色, c<=60. 每个节点一个bitset维护就可以. #in ...

  5. codeforces 633G. Yash And Trees dfs序+线段树+bitset

    题目链接 G. Yash And Trees time limit per test 4 seconds memory limit per test 512 megabytes input stand ...

  6. Educational Codeforces Round 6 E dfs序+线段树

    题意:给出一颗有根树的构造和一开始每个点的颜色 有两种操作 1 : 给定点的子树群体涂色 2 : 求给定点的子树中有多少种颜色 比较容易想到dfs序+线段树去做 dfs序是很久以前看的bilibili ...

  7. 【BZOJ-3252】攻略 DFS序 + 线段树 + 贪心

    3252: 攻略 Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 339  Solved: 130[Submit][Status][Discuss] D ...

  8. Codeforces 343D Water Tree(DFS序 + 线段树)

    题目大概说给一棵树,进行以下3个操作:把某结点为根的子树中各个结点值设为1.把某结点以及其各个祖先值设为0.询问某结点的值. 对于第一个操作就是经典的DFS序+线段树了.而对于第二个操作,考虑再维护一 ...

  9. BZOJ2434 [Noi2011]阿狸的打字机(AC自动机 + fail树 + DFS序 + 线段树)

    题目这么说的: 阿狸喜欢收藏各种稀奇古怪的东西,最近他淘到一台老式的打字机.打字机上只有28个按键,分别印有26个小写英文字母和'B'.'P'两个字母.经阿狸研究发现,这个打字机是这样工作的: 输入小 ...

随机推荐

  1. BZOJ4591——[Shoi2015]超能粒子炮·改

    1.题意:求 2.分析:公式恐惧症的同学不要跑啊QAQ 根据lucas定理-- 这一步大家都能懂吧,这是浅而易见的lucas定理转化过程,将每一项拆分成两项 那么下一步,我们将同类项合并 我们观察可以 ...

  2. Buddy内存分配算法

    Buddy(伙伴的定义): 这里给出伙伴的概念,满足以下三个条件的称为伙伴:1)两个块大小相同:2)两个块地址连续:3)两个块必须是同一个大块中分离出来的: Buddy算法的优缺点: 1)尽管伙伴内存 ...

  3. 将本地项目提交到coding上托管

    1:   注册coding并新建项目test2:在终端 cd 到要提交的项目  使用git init创建.git文件夹3:使用git pull  <项目地址>https的那个4:git a ...

  4. toast组件小结

    简介:toast是"吐司"的意思,它属于android杂项组件,是一个简单的消息提示框,类似于javascript中的alert. 作用 显示文本 显示图片 显示图文 3.常用方法 ...

  5. MFC2016.6.8

    1.theApp extern声明之后不可以使用?可以用,只是需要extern之后的类名和类名称写对,不要犯得低级错误.2.怎样取出列表控件中的第某列的值?GetItemText(); CListCt ...

  6. Java基础回顾

    学习基础背景:Acmer.有C/C++基础 以[Java语言程序设计(基础篇)]第10版为参考(感谢YJJ的推荐),列出部分知识点,注意思考背后的原因和好处坏处. [14-16章——关于可视化编程的章 ...

  7. 怎么写makefile?(转)

    跟我一起写 Makefile 陈皓 第一章.概述 什么是makefile?或许很多Winodws的程序员都不知道这个东西,因为那些Windows的IDE都为你做了这个工作,但我觉得要作一个好的和 pr ...

  8. 在jquery中,全选/全不选的表示方法

    <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/ ...

  9. Linux 相关面经

    都说没用过Linux都不要说自己搞过开发.我因为项目就是Linux没办法才接触Linux的,不过用了一段时间大黑屏外人看不懂的样子感觉还是屌屌的,虽说用过但知道也仅限于权限内的一些知识,还是一起看下面 ...

  10. [图像]判断图片是PNG还是JPG格式

    typedef NS_ENUM(NSInteger, NSPUIImageType) { NSPUIImageType_JPEG, NSPUIImageType_PNG, NSPUIImageType ...