【图论】找直径

树的直径

给定一个树,树中每条边有一个权值,树中两点间的距离定义为连接两点的路径边权之和。

树中距离最远的两个点间的距离被称为直径,连接这两个点的路径被称为最长链,也可以说是直径。

也就是说直径是一个数值概念,但同时也可指一条路径。直径可能不唯一。

我们一般认为这样一棵树是一棵带权无根树,即带权无向图。

求一棵树的直径

一般来说,树的直径有两种求法。

方法一:树形DP求树的直径

我们认为1号节点为树的根,那么这棵树就可以看作一棵有根树

设dep[ i ]为以i为节点的子树的最大深度,也可以理解为能够到达的最远的节点。

设它的子节点为son[ j ],那么dep[ i ] = max(son[ j ] + 边权)

然后,我们需要对每个节点i求出经过i点的最长链长度dp[ i ],那么整棵树的直径就很好求了,就是max(dp[ i ])

对于任意两个节点x,y,经过点i的最长链可以看成四个部分:从以x为根的子树中的最深点到x,从x到i,从i到y,从y到以y为根的子树中的最深点。

于是乎,dp[ i ] = max(dep[x] + dep[y] + 边权(x, i) + 边权(i, y))。

这样看起来有些复杂。

其实我们没有必要用两层循环来更新dp的值。在我们更新dep[ i ]的时候,当子节点枚举到x时,dep[ i ]中所保存的恰好就是从i到x加上从x到以x为根的子树中最深点,也就是dep[x] + 边(x, i)。

所以,我们可以先用dep

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值