题意:给你一个树,每条边都有边权,那么你就知道这可树上任意两点之间的距离,让你用这些距离,重新建一颗树,一颗最大生成树。
解:
在新树中,每个点连边要么和最长的连边要么就和次长的连边。
#include<stdio.h>
#include<iostream>
#include<string.h>
using namespace std;
#define en '\n'
#define ll long long
const ll inf=0x3f3f3f3f;
using namespace std;
const ll maxn =1e5+10;
inline ll read() {
char c = getchar(); ll x = 0, f = 1;
while(c < '0' || c > '9') {if(c == '-') f = -1; c = getchar();}
while(c >= '0' && c <= '9') x = x * 10 + c - '0', c = getchar();
return x ;
}
#define logm 18
#define max(a,b) (a>b?a:b)
#define min(a,b) (a<b?a:b)
using namespace std;
ll mx[maxn][logm],mi[maxn][logm],fa[maxn];
ll lg[maxn];
ll to[maxn][2];
struct node{
ll v,nxt,w;
}edge[maxn<<1];
ll tot,head[maxn],cnt;
void add(ll x,ll y,ll w){
++tot;
edge[tot].v=y;
edge[tot].nxt=head[x];
edge[tot].w=w;
head[x]=tot;
}
ll dp[maxn][2];
ll from[maxn],n,m;
void dfs_1(ll x,ll f){
dp[x][0]=dp[x][1]=0;
to[x][0]=to[x][1]=x;
for(ll i=head[x];i;i=edge[i].nxt){
ll y=edge[i].v;if(y==f)continue;
dfs_1(y,x);
ll va=edge[i].w;
if(dp[y][0]+va>dp[x][0]){
dp[x][1]=dp[x][0],to[x][1]=to[x][0];dp[x][0]=dp[y][0]+va,to[x][0]=to[y][0];
from[x]=y;
}
else if(dp[y][0]+va>dp[x][1]){
dp[x][1]=dp[y][0]+va,to[x][1]=to[y][0];
}
}
}
void dfs_2(ll x,ll f){
for(ll i=head[x];i;i=edge[i].nxt){
ll y=edge[i].v;if(y==f)continue;
if(from[x]!=y){
if(dp[y][0]<dp[x][0]+edge[i].w){
dp[y][1]=dp[y][0],to[y][1]=to[y][0];
dp[y][0]=dp[x][0]+edge[i].w,to[y][0]=to[x][0];
from[y]=x;
}
else if(dp[y][1]<dp[x][0]+edge[i].w){
dp[y][1]=dp[x][0]+edge[i].w,to[y][1]=to[x][0];
}
}
else{
if(dp[y][0]<dp[x][1]+edge[i].w){
dp[y][1]=dp[y][0],to[y][1]=to[y][0];
dp[y][0]=dp[x][1]+edge[i].w,to[y][0]=to[x][1];
from[y]=x;
}
else if(dp[y][1]<dp[x][1]+edge[i].w){
dp[y][1]=dp[x][1]+edge[i].w,to[y][1]=to[x][1];
}
}
dfs_2(y,x);
}
}
ll find(ll x){
if(x==fa[x])return x;
return fa[x]=find(fa[x]);
}
signed main() {
#ifdef local
freopen("input2.txt","r",stdin);
#endif // local
#define int register int
#define mem(a,b) memset(a,b,sizeof(a))
while(scanf("%lld",&n)!=EOF){
if(n==0 and m==0)break;
cnt=tot=0;
mem(head,0);
for(ll i=1;i<=n;i++)fa[i]=i;
for(ll i=1;i<n;++i){
ll x=read(),y=read(),w=read();
add(x,y,w),add(y,x,w);
}
dfs_1(1,0);dfs_2(1,0);
ll ans=0;
for(ll i=1;i<=n;i++){
ll y=to[i][0];
ll xx=find(i),yy=find(to[i][0]);
if(xx==yy){
yy=find(to[i][1]);
fa[xx]=yy;
ans+=dp[i][1];
}
else{
fa[xx]=yy;
ans+=dp[i][0];
}
} cout<<ans<<en;
}
return 0;
}