传送门 https://ac.nowcoder.com/acm/contest/1109#question
刚开始吓得我以为要搞树分治,差点就捞了哦!
这个定理要铭记于心啊!!!
#include<cstring> #include<iostream> #include<queue> #include<algorithm> #include<cstdio> #define maxn 100010 using namespace std; typedef long long ll; int n, m; struct Node { int p; int len; Node(int a, int b) :p(a), len(b) {} }; vector<Node>G[maxn]; void insert(int be, int en, int len) { G[be].push_back(Node(en, len)); } ll dis[maxn]; ll dis1[maxn]; ll dis2[maxn]; int dfs(int x, ll dep, int fa, ll d[]) { d[x] = dep; for (int i = 0; i < G[x].size(); i++) { int p = G[x][i].p; if (p == fa) continue; dfs(p, dep + G[x][i].len, x, d); } return 0; } int main() { while (~scanf("%d", &n)) { int be, en, len; for (int i = 0; i < n - 1; i++){ scanf("%d %d %d", &be, &en, &len); insert(be, en, len); insert(en, be, len); } int s=1, t=1; dfs(1, 0, -1, dis); for (int i = 1; i <= n; i++) { if (dis[i] > dis[s]) s = i; } dfs(s, 0, -1, dis1);//dis1从s开始 for (int i = 1; i <= n; i++) { if (dis1[i] > dis1[t]) t = i; } //t从s开始 dfs(t, 0, -1, dis2); ll ans = 0; for (int i = 1; i <= n; i++) { ans += max(dis1[i], dis2[i]); } ans -= dis1[t]; printf("%lld ", ans); for (int i = 0; i < maxn; i++) G[i].clear(); } return 0; }