With $Dsu \ on \ tree$ we can answer queries of this type:

How many vertices in the subtree of vertex $v$ has some property in $O (n \log n)$ time (for all of the queries)?

这题写的是轻重儿子(重链剖分)版本的 $Dsu \ on \ tree$

具体流程如下:

每次先递归计算轻儿子,再单独递归重儿子,计算完后轻儿子的一些信息需要删掉,但是重儿子的信息无需删除,如此出解,相当于是优化了暴力的多余部分

每个节点会作为轻儿子被计算,重链剖分上垂直有 $\log n$ 条链,故复杂度 $O (n \log n)$

代码

 #include <iostream>
#include <cstdio>
#include <cstring> using namespace std; typedef long long LL; const int MAXN = 1e05 + ;
const int MAXM = 1e05 + ;
const int MAXC = 1e05 + ; struct LinkedForwardStar {
int to; int next;
} ; LinkedForwardStar Link[MAXM << ];
int Head[MAXN]= {};
int size = ; void Insert (int u, int v) {
Link[++ size].to = v;
Link[size].next = Head[u]; Head[u] = size;
} int N;
int colour[MAXN]; int son[MAXN]= {};
int subsize[MAXN]= {};
void DFS (int root, int father) {
son[root] = - ;
subsize[root] = ;
for (int i = Head[root]; i; i = Link[i].next) {
int v = Link[i].to;
if (v == father)
continue;
DFS (v, root);
subsize[root] += subsize[v];
if (son[root] == - || subsize[v] > subsize[son[root]])
son[root] = v;
}
}
int vis[MAXN]= {};
int total[MAXC]= {};
int maxv = ;
LL sum = ;
void calc (int root, int father, int delta) { // 统计答案
total[colour[root]] += delta;
if (delta > && total[colour[root]] >= maxv) {
if (total[colour[root]] > maxv)
sum = , maxv = total[colour[root]];
sum += colour[root];
}
for (int i = Head[root]; i; i = Link[i].next) {
int v = Link[i].to;
if (v == father || vis[v])
continue;
calc (v, root, delta);
}
}
LL answer[MAXN]= {};
void Solve (int root, int father, int type) { // type表示是不是重儿子信息
for (int i = Head[root]; i; i = Link[i].next) {
int v = Link[i].to;
if (v == father || v == son[root])
continue;
Solve (v, root, );
}
if (~ son[root])
Solve (son[root], root, ), vis[son[root]] = ;
calc (root, father, );
answer[root] = sum;
if (~ son[root])
vis[son[root]] = ;
if (! type) // 如果是轻儿子信息就需删除
calc (root, father, - ), maxv = sum = ;
} int getnum () {
int num = ;
char ch = getchar (); while (! isdigit (ch))
ch = getchar ();
while (isdigit (ch))
num = (num << ) + (num << ) + ch - '', ch = getchar (); return num;
} int main () {
N = getnum ();
for (int i = ; i <= N; i ++)
colour[i] = getnum ();
for (int i = ; i < N; i ++) {
int u = getnum (), v = getnum ();
Insert (u, v), Insert (v, u);
}
DFS (, ), Solve (, , );
for (int i = ; i <= N; i ++) {
if (i > )
putchar (' ');
printf ("%lld", answer[i]);
}
puts (""); return ;
} /*
4
1 2 3 4
1 2
2 3
2 4
*/ /*
15
1 2 3 1 2 3 3 1 1 3 2 2 1 2 3
1 2
1 3
1 4
1 14
1 15
2 5
2 6
2 7
3 8
3 9
3 10
4 11
4 12
4 13
*/

Codeforces 600E - Lomsat gelral 「$Dsu \ on \ tree$模板」的更多相关文章

  1. Codeforces 600E Lomsat gelral(dsu on tree)

    dsu on tree板子题.这个trick保证均摊O(nlogn)的复杂度,要求资瓷O(1)将一个元素插入集合,清空集合时每个元素O(1)删除.(当然log的话就变成log^2了) 具体的,每次先遍 ...

  2. Codeforces 600E - Lomsat gelral(树上启发式合并)

    600E - Lomsat gelral 题意 给出一颗以 1 为根的树,每个点有颜色,如果某个子树上某个颜色出现的次数最多,则认为它在这课子树有支配地位,一颗子树上,可能有多个有支配的地位的颜色,对 ...

  3. Codeforces.600E.Lomsat gelral(dsu on tree)

    题目链接 dsu on tree详见这. \(Description\) 给定一棵树.求以每个点为根的子树中,出现次数最多的颜色的和. \(Solution\) dsu on tree模板题. 用\( ...

  4. Codeforces 600E Lomsat gelral (树上启发式合并)

    题目链接 Lomsat gelral 占坑……等深入理解了再来补题解…… #include <bits/stdc++.h> using namespace std; #define rep ...

  5. Codeforces 600E. Lomsat gelral(Dsu on tree学习)

    题目链接:http://codeforces.com/problemset/problem/600/E n个点的有根树,以1为根,每个点有一种颜色.我们称一种颜色占领了一个子树当且仅当没有其他颜色在这 ...

  6. codeforces 600E Lomsat gelral

    题面:codeforces600E 学习一下$dsu \ on \ tree$.. 这个东西可以处理很多无修改子树问题,复杂度通常为$O(nlogn)$. 主要操作是:我们先把整棵树链剖一下,然后每次 ...

  7. codeforces 600E. Lomsat gelral 启发式合并

    题目链接 给一颗树, 每个节点有初始的颜色值. 1为根节点.定义一个节点的值为, 它的子树中出现最多的颜色的值, 如果有多种颜色出现的次数相同, 那么值为所有颜色的值的和. 每一个叶子节点是一个map ...

  8. codeforces 600E . Lomsat gelral (线段树合并)

    You are given a rooted tree with root in vertex 1. Each vertex is coloured in some colour. Let's cal ...

  9. 【Codeforces】600E. Lomsat gelral

    Codeforces 600E. Lomsat gelral 学习了一下dsu on tree 所以为啥是dsu而不是dfs on tree??? 这道题先把这棵树轻重链剖分了,然后先处理轻儿子,处理 ...

随机推荐

  1. 利用mask-image蒙层编写异形头像

    需求:后台给了一个规规矩矩的头像,或圆或方,UI要求展示成水滴的形状.正在想到底如何实现的时候,不由自主去翻了鑫神的博客,正好找到了答案,窃喜(·_·) UI给的形状: 后台给的头像(忽略橙色背景色, ...

  2. PhpStorm 配置本地断点调试

    前言: 有够拖延症的,应该是一年多以前就使用过PhpStorm的debug断点调试了吧,不够过当时是别人帮我配的,我记得还挺复杂.后来重装系统后尝试了配置,好像没成吧,记得当初老师帮我配也没成(... ...

  3. Alpha 冲刺四

    团队成员 051601135 岳冠宇 051604103 陈思孝 031602629 刘意晗 031602248 郑智文 031602234 王淇 会议照片 项目燃尽图 项目进展 实现后端聊天接收,搜 ...

  4. SQL 中LTrim、RTrim与Trim的用法

    LTrim.RTrim与 Trim 函数 返回 Variant (String),其中包含指定字符串的拷贝,没有前导空白 (LTrim).尾随空白 (RTrim) 或前导和尾随空白 (Trim).语法 ...

  5. Vue-router的基本用法

    刚学习vue不久,就接触了路由这个好东西.下面简单聊聊vue-router的基本用法. 一.路由的概念 路由,其实就是指向的意思,当我点击页面上的home按钮时,页面中就要显示home的内容,如果点击 ...

  6. tomcat Failed creating java C:\Program Files\Java\jre6\bin\client\jvm.dll %1 不是有效的 Win32 应用程序。

    jdk版本搞的鬼 请下载64位的jdkj进行安装

  7. 走楼梯(walk) 解题报告

    走楼梯(walk) 题意 给一个长为\(n(1\le n\le 10^5)\)序列\(\{a\}\),每次从中间挖掉\([l,r]\),然后询问最长上升子序列,强制在线. 有一档分是30000和离线, ...

  8. 前端学习 -- Css -- 字体的几个属性学习

    font-style可以用来设置文字的斜体 - 可选值: normal,默认值,文字正常显示 italic 文字会以斜体显示 oblique 文字会以倾斜的效果显示 - 大部分浏览器都不会对倾斜和斜体 ...

  9. 20145215《网络对抗》Exp2 后门原理与实践

    20145215<网络对抗>Exp2 后门原理与实践 基础问题回答 例举你能想到的一个后门进入到你系统中的可能方式? 在网上下载软件的时候,后门很有可能被捆绑在下载的软件当中: 浏览网页的 ...

  10. vue中assets文件夹与static文件夹的区别

    1.如果这些产品图片文件“万年不变”,放在 /static 目录里,(不需要使用require将这些图片作为模块来引用) var products = [{ img: '/static/img/pro ...