HUD 5176 The Experience of Love

来源:互联网 发布:淘宝买管制刀具 编辑:程序博客网 时间:2024/05/01 16:09

题解:
1.按边权排序
2.按顺序将边加到集合中,可以用到并查集
总结:
1.这道题目没有做出来,看了题解说是用并查集来做才想出来一个比较麻烦的做法,后来再看题解,对代码稍微优化了一些,但我觉得应该还是有能力做出来的,如果用笔画一画的话
2.其实优化这一步很容易想出来,就是正着排序和反着排序的问题,说明思考问题还是不够全面,不够优化
3.看到一个论文讲解如何解题:《how to solve it》
4.弄清问题:(1)弄清所有已知条件,最好是图+文
5.拟定计划:(1).找到类似题目类比(2).重述此问题,从不同的角度思考(3).把这个问题更加普遍特殊的展示出来
6.实行计划:(1).检查
7.回顾:(1).能否用其他的方法解决这个问题(2).能否把这个问题推广

#pragma comment(linker, "/STACK:1024000000,1024000000")#include<iostream>#include<cstring>#include<cstdio>#include<algorithm>using namespace std;typedef unsigned long long ull;#define MAXN 150005struct Edge{    int u,v;    ull w;    bool operator < (const Edge & n)const{        return w < n.w;    }}e[MAXN];int n,f[MAXN],cnt[MAXN];ull ans;void init(){    for(int i = 1;i <= n;i++)    {        f[i] = i;        cnt[i] = 1;    }}int findfa(int i){    return f[i] == i ? i : f[i] = findfa(f[i]);}void Union(int u,int v,ull w,bool flag){    int fu = findfa(u),fv = findfa(v);    if(flag)        ans += w * cnt[fu] * cnt[fv];    else        ans -= w * cnt[fu] * cnt[fv];    f[fv] = fu;    cnt[fu] += cnt[fv];}int main(){    int _ = 1;    while(scanf("%d",&n) != EOF)    {        for(int i = 0;i < n - 1;i++)            scanf("%d%d%llu",&e[i].u,&e[i].v,&e[i].w);        sort(e,e + n - 1);        ans = 0;        init();        for(int i = 0;i < n - 1;i++)            Union(e[i].u,e[i].v,e[i].w,true);        init();        for(int i = n - 2;i >= 0;i--)            Union(e[i].u,e[i].v,e[i].w,false);         printf("Case #%d: %llu\n",_++,ans);    }}
0 0
原创粉丝点击