牛客练习赛27 水图(思维+暴搜)

画几个图就可以发现,经过每个点最少一次的最短路径即使,总边权*2-从x点出发走的一个最长的路径,可以想象成这个最长的路径对应的分支是最后走的,走到了该分支的叶子节点,就满足要求了,就不必回到x点了,

​#include<bits/stdc++.h>
using namespace std;
#define ll long long
const int maxn=50000+10;
struct edge
{
    int v,w,nxt;
    edge(int vv=0,int ww=0,int nxtt=0)
    {
        v=vv;
        w=ww;
        nxt=nxtt;
    }
}e[2*maxn];
int head[maxn];
ll maxx=-1;
void dfs(int now,int fa,ll dis)
{
    for(int i=head[now];i!=-1;i=e[i].nxt)
    {
        int v=e[i].v,w=e[i].w;
        if(v==fa) continue;
        dfs(v,now,dis+w);
    }
    maxx=max(dis,maxx);
}
int main()
{
    ll ans=0;
    int n,x,cnt=0;
    scanf("%d %d",&n,&x);
    memset(head,-1,sizeof(head));
    for(int i=1;i<n;i++)
    {
        int u,v,w;
        scanf("%d %d %d",&u,&v,&w);
        e[cnt]=edge(v,w,head[u]);
        head[u]=cnt++;
        e[cnt]=edge(u,w,head[v]);
        head[v]=cnt++;
        ans+=w;
    }
    ans*=2;
    dfs(x,-1,0);
    printf("%lld
",ans-maxx);
    return 0;

}
​
原文地址:https://www.cnblogs.com/eason9906/p/11754865.html