道路改建

题目描述 一个由n户人家组成的村庄,用n-1条路径连接,形成一棵树。
现在进行道路改建,先把某条边的删除,再用这条边连接其他两个点(保持长度相同)。
使得最后村庄之间仍能相互到达,且最远的两个村庄之间的距离最小。
输入 第一行一个整数n,表示村庄的个数。
接下来n-1行,每行3个整数a、b、c,表示有一条路径连接编号为a和b的村庄(编号从0开始)。
输出 输出可以使最远距离达的最小值。
对于100%的数据,n的范围[1,5000],0≤a,b≤n-1,1≤c≤10000;

一道很不错的树的题目
主要的思考点在于
如何找到树上任意一结点的最远值和如何更新答案

根据题目描述
在切断一条边后
一棵树(A)会被分成两棵树(B,C)
这时答案会有三种情况:
1.B的直径
2.C的直径
3.两棵树重新连接后形成的新的直径

我们要做的就是使3最小
设新边连接两点为a,b
这个直径的组成为len1+len2+len3
len1为a在A树上的最远距离
len2为b在B树上的最远距离
len3为被删除边的长度

先在要解决的就是如何快速地求出每个点的最远距离
这里可以使用三遍dfs
第一次找到最远点x1
第二次找到直径的另一个端点x2(同时求出每个点到x1的距离)
第三次从x2出发,求出x2到任意点的距离
ps:节点的距离最大值一定是直径两个端点的任意一点

为了使代码较为简洁可以用结构体包起来

#include<iostream>
#include<cstdio>
  • 3
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值