【题解】CF741D(DSU on TREE)
【题解】CF741D(DSU on TREE)
写一写这道题来学习学习模板
用二进制来转换一下条件,现在就是要求一下\(lowbit(x)=x\)的那些路径了。
DSU on TREE 是这样一种算法:
- 像树剖一样分出轻重链,根据那套理论可知轻边\(O(\log n)\)。
- 递归处理一个节点的所有轻儿子,并且回溯的时候将统计信息清空。
- 递归处理一个节点的那个重儿子,并且回溯的时候保留统计信息。
- 获得重儿子信息后,遍历一下所有轻儿子统计答案。
分析复杂度:对于每个点,可以被他父亲所有的轻边多遍历一次。复杂度\(O(tn \log n)\),\(t\)是加入一个信息需要的复杂度。
具体到这道题的话,就是开桶记录该二进制状态下最深深度点的深度。取\(max\)就好
//@winlere
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<vector>
using namespace std; typedef long long ll;
inline int qr(){
register int ret=0,f=0;
register char c=getchar();
while(c<48||c>57)f|=c==45,c=getchar();
while(c>=48&&c<=57) ret=ret*10+c-48,c=getchar();
return f?-ret:ret;
}
char c;
const int maxn=5e5+5,inf=1e9;
int d[maxn],cnt[1<<22|1],n,siz[maxn],son[maxn],dfn[maxn],End[maxn],arc[maxn];
int ans[maxn],dis[maxn];
vector< pair<int,int> > e[maxn];
inline void add(const int&fr,const int&to,const int&w){
e[fr].push_back({to,1<<w});
}
void predfs(const int&now){
siz[now]=1;
dfn[now]=++*dfn;
arc[*dfn]=now;
for(auto t:e[now])
d[t.first]=d[now]^t.second,dis[t.first]=dis[now]+1,predfs(t.first),siz[now]+=siz[t.first],son[now]=siz[t.first]>siz[son[now]]?t.first:son[now];
End[now]=*dfn;
}
void dfs(const int&now,const int&keep){
for(auto t:e[now])
if(t.first^son[now])
dfs(t.first,0),ans[now]=max(ans[now],ans[t.first]);
if(son[now]) dfs(son[now],1),ans[now]=max(ans[now],ans[son[now]]);
if(cnt[d[now]]) ans[now]=max(ans[now],cnt[d[now]]-dis[now]);
for(int t=0;t<22;++t)
if(cnt[d[now]^(1<<t)])
ans[now]=max(ans[now],cnt[d[now]^(1<<t)]-dis[now]);
cnt[d[now]]=max(cnt[d[now]],dis[now]);
for(auto T:e[now])
if(T.first^son[now]){
for(int t=dfn[T.first];t<=End[T.first];++t){
if(cnt[d[arc[t]]])
ans[now]=max(ans[now],cnt[d[arc[t]]]+dis[arc[t]]-dis[now]*2);
for(int i=0;i<22;++i)
if(cnt[d[arc[t]]^(1<<i)])
ans[now]=max(ans[now],cnt[d[arc[t]]^(1<<i)]+dis[arc[t]]-dis[now]*2);
}
for(int t=dfn[T.first];t<=End[T.first];++t)
cnt[d[arc[t]]]=max(cnt[d[arc[t]]],dis[arc[t]]);
}
if(!keep) for(int t=dfn[now];t<=End[now];++t) cnt[d[arc[t]]]=0;
}
int main(){
n=qr();
for(int t=2,t1;t<=n;++t){
t1=qr();
char c=getchar();
while(c<'a'||c>'z') c=getchar();
add(t1,t,c-'a');
}
predfs(1);
dfs(1,0);
for(int t=1;t<=n;++t) printf("%d ",ans[t]);
putchar('\n');
return 0;
}
【题解】CF741D(DSU on TREE)的更多相关文章
- 【DSU on tree】【CF741D】Arpa’s letter-marked tree and Mehrdad’s Dokhtar-kosh paths
Description 给定一棵 \(n\) 个节点的树,每条边上有一个字符,字符集大小 \(22\),求每个节点的子树内最长的简单路径使得路径上的字符经过重排后构成回文串. Limitation \ ...
- 【题解】Arpa's letter-marked tree and Mehrdad's Dokhtar-kosh paths Codeforces 741D DSU on Tree
Prelude 很好的模板题. 传送到Codeforces:(* ̄3 ̄)╭ Solution 首先要会DSU on Tree,不会的看这里:(❤ ω ❤). 众所周知DSU on Tree是可以用来处 ...
- CF741D Arpa’s letter-marked tree and Mehrdad’s Dokhtar-kosh paths(dsu on tree)
一棵根为1 的树,每条边上有一个字符(a-v共22种). 一条简单路径被称为Dokhtar-kosh当且仅当路径上的字符经过重新排序后可以变成一个回文串. 求每个子树中最长的Dokhtar-kosh路 ...
- dsu on tree (树上启发式合并) 详解
一直都没出过算法详解,昨天心血来潮想写一篇,于是 dsu on tree 它来了 1.前置技能 1.链式前向星(vector 建图) 2.dfs 建树 3.剖分轻重链,轻重儿子 重儿子 一个结点的所有 ...
- CF 741D. Arpa’s letter-marked tree and Mehrdad’s Dokhtar-kosh paths [dsu on tree 类似点分治]
D. Arpa's letter-marked tree and Mehrdad's Dokhtar-kosh paths CF741D 题意: 一棵有根树,边上有字母a~v,求每个子树中最长的边,满 ...
- UOJ#266. 【清华集训2016】Alice和Bob又在玩游戏 博弈,DSU on Tree,Trie
原文链接https://www.cnblogs.com/zhouzhendong/p/UOJ266.html 题解 首先我们可以直接暴力 $O(n^2)$ 用 sg 函数来算答案. 对于一个树就是枚举 ...
- dsu on tree入门
先瞎扯几句 说起来我跟这个算法好像还有很深的渊源呢qwq.当时在学业水平考试的考场上,题目都做完了不会做,于是开始xjb出题.突然我想到这么一个题 看起来好像很可做的样子,然而直到考试完我都只想出来一 ...
- 洛谷P4482 [BJWC2018]Border 的四种求法 字符串,SAM,线段树合并,线段树,树链剖分,DSU on Tree
原文链接https://www.cnblogs.com/zhouzhendong/p/LuoguP4482.html 题意 给定一个字符串 S,有 q 次询问,每次给定两个数 L,R ,求 S[L.. ...
- [学习笔记]Dsu On Tree
[dsu on tree][学习笔记] - Candy? - 博客园 题单: 也称:树上启发式合并 可以解决绝大部分不带修改的离线询问的子树查询问题 流程: 1.重链剖分找重儿子 2.sol:全局用桶 ...
随机推荐
- Python类型模块:types
types模块中定义了Python中所有的类型,包括NoneType, TypeType, IntType, FloatType, BooleanType, BufferType, Bui ...
- C++:只用初始化列表初始化变量的几种情况
1.类成员函数中const变量的初始化(也就是第一点) 有几个容易混淆的地方: (1)const 的变量只能通过构造函数的初始化列表进行初始化:(貌似在C++11中可以正常编译) (2)static ...
- linux更新系统时间
查看时间 date 更新时间 yum install ntpdate ntpdate time.windows.com
- mosquitto/openssl 在RK3288上的编译以及MQTT客户端的代码示例
1,依赖库openssl 的交叉编译 (1)配置编译器信息 setarch i386 ./config no-asm shared --cross-compile-prefix=arm-linux-a ...
- css3鼠标移动图片上移效果
css3的功能真是很强大,学无止境,不多说,直接上代码 css部分: <style> ;;} .text-center{text-align:center} .col_cont{width ...
- Ant Design的Form组件中FormItem名称相同引起的问题
1.问题描述 在使用Antd组件Form表单的过程中,会出现FormItem同名的情况,此时要特别注意同名引起的表单行为异常问题,主要表现在以下方面: (1)同名表单项的值共享,并且其中一个的值改变, ...
- CentOS7.0下安装FTP服务的方法
http://www.jb51.net/article/106604.htm 本篇文章主要介绍了CentOS7.0下安装FTP服务的方法,小编觉得挺不错的,现在分享给大家,也给大家做个参考.一起跟 ...
- [转]什么是CNN、RNN、LSTM
. 全连层 每个神经元输入: 每个神经元输出: (通过一个激活函数) 2. RNN(Recurrent Neural Network) 与传统的神经网络不通,RNN与时间有关. 3. LSTM(Lon ...
- [转]java常用正则表达式
只能输入数字:"^[0-9]*$". 只能输入n位的数字:"^\d{n}$". 只能输入至少n位的数字:"^\d{n,}$". 只能输 ...
- springboot整合mybatis完整示例, mapper注解方式和xml配置文件方式实现(我们要优雅地编程)
一.注解方式 pom <dependency> <groupId>org.mybatis.spring.boot</groupId> <artifactId& ...