问题描述

Just in case somebody missed it: we have wonderful girls in Arpa’s land.

Arpa has a rooted tree (connected acyclic graph) consisting of n vertices. The vertices are numbered 1through n, the vertex 1 is the root. There is a letter written on each edge of this tree. Mehrdad is a fan of Dokhtar-kosh things. He call a string Dokhtar-kosh, if we can shuffle the characters in string such that it becomes palindrome.

He asks Arpa, for each vertex v, what is the length of the longest simple path in subtree of v that form a Dokhtar-kosh string.

输入格式

The first line contains integer n (1  ≤  n  ≤  5·105) — the number of vertices in the tree.

(n  -  1) lines follow, the i-th of them contain an integer pi + 1 and a letter ci + 1 (1  ≤  pi + 1  ≤  i, ci + 1 is lowercase English letter, between a and v, inclusively), that mean that there is an edge between nodes pi + 1 and i + 1 and there is a letter ci + 1 written on this edge.

输出格式

Print n integers. The i-th of them should be the length of the longest simple path in subtree of the i-th vertex that form a Dokhtar-kosh string.

样例输入输出

Examples

Input

4
1 s
2 a
3 s

Output

3 1 1 0

Input

1 a
2 h
1 a
4 h

Output

4 1 0 1 0

题意概括

有一棵树,每条边上都有一个字母,求每棵子树中最长的简单路径使这条路径上的所有字符与根节点到该点路径上的字符重新排列后能组成回文字符串。

解析

第一步,我们来分析题目中最特殊的一点:回文串。一个字符串是回文串,当且仅当字符串中最多有一个字符出现了奇数次。我们需要一个结构来表述一个字符串使我们能够清晰地知道每个字符串出现次数的奇偶。由于只有22个字母,我们可以状态压缩,每个位置上的字母出现奇数次则为1,偶数次则为0,实现可用异或运算。

既然是子树问题,我们就可以用树上启发式合并来写。设\(f[i]\)表示状态为\(i\)的最长的字符串的最大深度(要求字符串没有在两棵子树中),那么每次更新答案时,假设当前节点为\(x\),从根节点到\(x\)的路径状态压缩后表示为\(xor[x]\)。下面分两种情况讨论:

1.字符串不会跨过子树的根节点。此时又有两种情况:

  • \(f[xor[x]]\)有值,说明在这棵子树中,有一条路径上的情况与\(x\)到根节点的路径一定能构成回文串(异或后全为0)。因此,有
    \[ ans[x]=max(ans[x],f[xor[x]]) \]

  • 假设能满足要求的路径为\(path\),那么\(xor[x]^path\)得到的结果一定是某一位为1或全为0。因此,有异或运算的性质,可以直接用\(xor[x]^(1<<i)\)得到满足要求的状态,再更新答案,有
    \[ ans[x]=max(ans[x],f[xor[x]\oplus(1<<i)]) \]

同时,还要更新对应的\(f\)值,
\[ f[xor[x]]=max(f[xor[sum]],dep[x]) \]
其中\(dep[x]\)表示点\(x\)的深度。

2.字符串会跨过子树的根节点。那么我们可以通过情况1的方法一样来进行,只不过会对子树中每一个节点统计一次答案。具体可以用时间戳来实现模拟子树递归。另外,每遍历完一棵子树,都要记得更新一下\(f\)。

代码

#include <iostream>
#include <cstdio>
#define N 500002
using namespace std;
int head[N],ver[N],nxt[N],edge[N],l;
int n,i,son[N],size[N],dep[N],sum[N],dfn[N],low[N],rec[N],ans[N],tim,f[1<<23];
void insert(int x,int y,char z)
{l++;ver[l]=y;edge[l]=(1<<(int)(z-'a'));nxt[l]=head[x];head[x]=l;
}
void dfs(int x,int pre)
{dfn[x]=++tim;rec[tim]=x;size[x]=1;dep[x]=dep[pre]+1;for(int i=head[x];i;i=nxt[i]){int y=ver[i];if(y!=pre){sum[y]=sum[x]^edge[i];dfs(y,x);size[x]+=size[y];if(size[y]>size[son[x]]) son[x]=y;}}low[x]=tim;
}
void dsu(int x,int pre)
{for(int i=head[x];i;i=nxt[i]){int y=ver[i];if(y!=son[x]){dsu(y,x);ans[x]=max(ans[x],ans[y]);for(int j=dfn[y];j<=low[y];j++) f[sum[rec[j]]]=0;}}if(son[x]>0){dsu(son[x],x);ans[x]=max(ans[x],ans[son[x]]);}if(f[sum[x]]) ans[x]=max(ans[x],f[sum[x]]-dep[x]);for(int i=0;i<22;i++){if(f[sum[x]^(1<<i)]) ans[x]=max(ans[x],f[sum[x]^(1<<i)]-dep[x]);}f[sum[x]]=max(f[sum[x]],dep[x]);for(int i=head[x];i;i=nxt[i]){int y=ver[i];if(y!=son[x]){for(int j=dfn[y];j<=low[y];j++){int z=rec[j];if(f[sum[z]]) ans[x]=max(ans[x],f[sum[z]]+dep[z]-2*dep[x]);for(int k=0;k<22;k++){if(f[sum[z]^(1<<k)]) ans[x]=max(ans[x],f[sum[z]^(1<<k)]+dep[z]-2*dep[x]);}}for(int j=dfn[y];j<=low[y];j++){int z=rec[j];f[sum[z]]=max(f[sum[z]],dep[z]);}}}
}
int main()
{cin>>n;for(i=1;i<n;i++){int u;char w;cin>>u>>w;insert(u,i+1,w);}dfs(1,0);dsu(1,0);for(i=1;i<=n;i++) cout<<ans[i]<<' ';cout<<endl;return 0;
}

转载于:https://www.cnblogs.com/LSlzf/p/10988331.html

[CF741D] Arpa’s letter-marked tree and Mehrdad’s Dokhtar-kosh paths相关推荐

  1. CF741D Arpa’s letter-marked tree and Mehrdad’s Dokhtar-kosh paths

    CF741D Arpa's letter-marked tree and Mehrdad's Dokhtar-kosh paths 好像这个题只能Dsu On Tree? 有根树点分治 统计子树过x的 ...

  2. Codeforces 741 D - Arpa’s letter-marked tree and Mehrdad’s Dokhtar-kosh paths

    D - Arpa's letter-marked tree and Mehrdad's Dokhtar-kosh paths 思路: 树上启发式合并 从根节点出发到每个位置的每个字符的奇偶性记为每个位 ...

  3. (树上启发式合并)CF741D Arpa’s letter-marked tree and Mehrdad’s Dokhtar-kosh paths

    整理的算法模板合集: ACM模板 点我看算法全家桶系列!!! 实际上是一个全新的精炼模板整合计划 Weblink https://www.luogu.com.cn/problem/CF741D Pro ...

  4. CF741D Arpa’s letter-marked tree and Mehrdad’s Dokhtar-kosh paths 树启 + 状压

    传送门 文章目录 题意: 思路: 题意: 思路: 据说是树启的压轴题. 先观察题意,字符有1−221-221−22中,为什么不是1−261-261−26个?显然他就是让你状压的.我们考虑将每条路径上字 ...

  5. [Codeforces741D]Arpa's letter-marked tree and Mehrdad's Dokhtar-kosh paths——dsu on tree

    题目链接: Codeforces741D 题目大意:给出一棵树,根为$1$,每条边有一个$a-v$的小写字母,求每个点子树中的一条最长的简单路径使得这条路径上的边上的字母重排后是一个回文串. 显然如果 ...

  6. 【CodeForces】741 D. Arpa’s letter-marked tree and Mehrdad’s Dokhtar-kosh paths(dsu on tree)

    [题意]给定n个点的树,每条边有一个小写字母a~v,求每棵子树内的最长回文路径,回文路径定义为路径上所有字母存在一种排列为回文串.n<=5*10^5. [算法]dsu on tree [题解]这 ...

  7. 树上启动式合并问题 ---- D. Arpa’s letter-marked tree and Mehrdad’s Dokhtar-kosh paths [状态压缩+树上启发式合并]

    题目链接 题目大意: 一棵根为1 的树,每条边上有一个字符(a−va−va−v共22种). 一条简单路径被称为Dokhtar−kosh当且仅当路径上的字符经过重新排序后可以变成一个回文串. 求每个子树 ...

  8. CF741D-Arpa's letter-marked tree and Mehrdad's Dokhtar-kosh paths【树上启发式合并】

    正题 评测记录:https://www.luogu.org/recordnew/lists?uid=52918&pid=CF741D 题目大意 一棵根为111的树,每条边上有一个字符(a−v( ...

  9. 暑假训练-义乌(7.8-7.15)

    暑假训练 模拟赛 图表 数据 7.8(lxl) 7.9(lxl) 7.10(lxl) 7.11(lxl) 7.12(wls) 7.13(wls) 7.14(wls) 7.15(lfds) 训练 数据结 ...

最新文章

  1. AI打败外科医生:机器人做手术,你敢来一刀吗?
  2. php生成静态页面并预览
  3. Bug反思:减少笔误
  4. 学习笔记(53):Python实战编程-Checkbutton
  5. 重新学习c++--理解引用、智能指针、虚函数、模板、容器
  6. 牛客假日团队赛1 A.蹄球锦标赛
  7. js 指定年月获取最后天
  8. Atitit.有分区情况下的表查询策略流程
  9. 计算机说课稿模板小学数学,小学数学优质说课稿模板
  10. PPT怎么切换不同的母版
  11. 行业边缘丨中国电科发布“海雀”处理器;中科海微获千万融资;联想发布边缘服务器;风河加入CNCF云原生计算基金会成为银牌会员;...
  12. AI视觉千亿规模市场虚席以待 初创企业看好“算法决定芯片”路径
  13. android遥控杆控件,Android自定义滑杆控件SeekBar多功能版本
  14. Tomcat部署及安装
  15. react组件React slick的使用
  16. SpringCloud系列之六
  17. windows10进入/退出管理员账户(Administrator)方法
  18. 朴素贝叶斯算法及贝叶斯网络详述
  19. [安洵杯 2019]吹着贝斯扫二维码
  20. 理解逆矩阵 理解单位矩阵

热门文章

  1. android camera2 qcom,lineage编译环境里,编译QCamera2的技术总结
  2. asp.net捕获全局未处理异常的几种方法
  3. Rest Framework:二、序列化组件
  4. JavaScript基础(六)面向对象
  5. stackless python初体验
  6. 文博项目-终端网口测试-软件
  7. C#里枚举类型以及值引用和地址引用差别演示代码
  8. 为什么我突然不能启动tomcat_为什么我的Tomcat启动加载不了配置文件?
  9. mysql varchar,bigint,char三种类型性能的比较
  10. 邮件退订_如何方便地退订邮件列表