Cow Politics G

一个树上每一个点都有一个组别,求相同组别的点对相差的最大距离。可以叫这题为“部分树的直径”

有一个结论:对于任意一个组别,深度最大的点一定在答案的点对里。

审视一下这个证明是如何分类的,对于LCA的部分,显然是通过讨论y是不是z的祖先来完成的;之后是通过讨论是否是子树来进行的

所以,对于不同组别,我们只需要求出深度最大的点即可,之后在跑一遍LCA即可,均摊下来O(N)

然而,这道题目还有更简单的做法

既然是与直径有关,我们回想一下BFS求树的直径是怎么求的

回想完后,我们回到这道题目,对于一个组别,我们把有关这个组别的极大子树(即度数为1的点都是由这个组别的点构成的,而且这个组别的所有点都在这个子树里面)提出来,如果我们能够对每个组别的极大子树求出直径,那么显然就是答案(因为极大子树的边界都是这个组别的点,而极大子树的直径又一定是以边界作为端点的)

我们模仿BFS的过程,首先求出每个组别直径的端点,只需要在dfs遍历原树的时候,对于当前点:

如果当前点所在组别没被标记,则标记,并把当前点作为其组别的代表

如果当前点所在组别已经被标记,则用当前点与其组别代表求距离,并记录下其组别距离的最大值

一遍dfs完了之后,我们就相当于对每个极大子树求出了一个直径的端点,之后再dfs一遍,并模仿类似过程就可以解决问题了

posted @   最爱丁珰  阅读(3)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· 阿里巴巴 QwQ-32B真的超越了 DeepSeek R-1吗?
· 【译】Visual Studio 中新的强大生产力特性
· 10年+ .NET Coder 心语 ── 封装的思维:从隐藏、稳定开始理解其本质意义
· 【设计模式】告别冗长if-else语句:使用策略模式优化代码结构
点击右上角即可分享
微信分享提示