F. Imbalance Value of a Tree



题意:

给一颗带点权的树,求所有简单路径上最大点权和最小点权之差的总和。

思路:

所求问题可以看作求各路径上的最大值之和减各路径上的最小值之和。因此考虑每个点权的贡献次数,也就是他们成为最值的次数。

以求最大值之和为例分析问题,我们可以从最小点权开始统计,每次将最小点加入。这样做的好处是每次取出的点,一定是当前已取出点中最大的,即当前任何经过该点的路径的最大值一定是它。已加入的点用并查集来维护连通块大小,以便于统计。该点所在连通块和与该点相连的连通块的大小相乘,可以求出这两个块经过该点的路径条数,然后将相连的块合并到该点所在的块,与下一个相连的连通块再继续做同样的处理。按点权从小到大的顺序,对每个点这样处理即可算出每个点成为最大值的次数。

求最小值之和同理。

代码:

  1. #include<bits/stdc++.h>
  2. #define dd(x) cout<<#x<<" = "<<x<<" "
  3. #define de(x) cout<<#x<<" = "<<x<<"\n"
  4. #define sz(x) int(x.size())
  5. #define All(x) x.begin(),x.end()
  6. #define pb push_back
  7. #define mp make_pair
  8. #define fi first
  9. #define se second
  10. using namespace std;
  11. typedef long long ll;
  12. typedef long double ld;
  13. typedef pair<int,int> P;
  14. typedef priority_queue<int> BQ;
  15. typedef priority_queue<int,vector<int>,greater<int> > SQ;
  16. const int maxn=1e6+10,mod=1e9+7,INF=0x3f3f3f3f;
  17. vector<int> G[maxn];
  18. P w[maxn];
  19. ll sum[maxn],fa[maxn];
  20. bool vis[maxn];
  21. void init(int n)
  22. {
  23. for (int i=1;i<=n;++i)
  24. fa[i]=i,sum[i]=1,vis[i]=0;
  25. }
  26. int find(int x)
  27. {
  28. return fa[x]==x?x:fa[x]=find(fa[x]);
  29. }
  30. ll unio(int u)
  31. {
  32. ll tmp=0;
  33. for (auto& v:G[u])
  34. {
  35. if (!vis[v])
  36. continue;
  37. int fv=find(v);
  38. tmp+=sum[fv]*sum[u];
  39. fa[fv]=u,sum[u]+=sum[fv];
  40. }
  41. return tmp;
  42. }
  43. int main()
  44. {
  45. int n;
  46. cin>>n;
  47. for (int i=1;i<=n;++i)
  48. {
  49. scanf("%d",&w[i].fi);
  50. w[i].se=i;
  51. }
  52. for (int i=1;i<n;++i)
  53. {
  54. int u,v;
  55. scanf("%d%d",&u,&v);
  56. G[u].pb(v);
  57. G[v].pb(u);
  58. }
  59. sort(w+1,w+1+n);
  60. ll ans=0;
  61. init(n);
  62. for (int i=1;i<=n;++i)
  63. {
  64. ans+=unio(w[i].se)*w[i].fi;
  65. vis[w[i].se]=1;
  66. }
  67. init(n);
  68. for (int i=n;i;--i)
  69. {
  70. ans-=unio(w[i].se)*w[i].fi;
  71. vis[w[i].se]=1;
  72. }
  73. cout<<ans;
  74. return 0;
  75. }

Codeforces 915 F. Imbalance Value of a Tree(并查集)的更多相关文章

  1. 【CodeForces】915 F. Imbalance Value of a Tree 并查集

    [题目]F. Imbalance Value of a Tree [题意]给定n个点的带点权树,求所有路径极差的和.n,ai<=10^6 [算法]并查集 [题解]先计算最大值的和,按点权从小到大 ...

  2. CF915F Imbalance Value of a Tree (并查集)

    题目大意:给你一棵树,每个点有点权a_{i},求$\sum _{i=1}^{n} \sum _{j=i}^{n} f(i,j)$,$f(i,j)$表示i,j,路径上的点的最大权值-最小权值 正解的思路 ...

  3. [Swust OJ 856]--Huge Tree(并查集)

    题目链接:http://acm.swust.edu.cn/problem/856/ Time limit(ms): 1000 Memory limit(kb): 10000 Description T ...

  4. Educational Codeforces Round 64 (Rated for Div. 2)D(并查集,图)

    #include<bits/stdc++.h>using namespace std;int f[2][200007],s[2][200007];//并查集,相邻点int find_(in ...

  5. Codeforces 699D Fix a Tree 并查集

    原题:http://codeforces.com/contest/699/problem/D 题目中所描述的从属关系,可以看作是一个一个块,可以用并查集来维护这个森林.这些从属关系中会有两种环,第一种 ...

  6. Codeforces Round #363 (Div. 2)D. Fix a Tree(并查集)

    D. Fix a Tree time limit per test 2 seconds memory limit per test 256 megabytes input standard input ...

  7. Codeforces Round #363 (Div. 2) D. Fix a Tree —— 并查集

    题目链接:http://codeforces.com/contest/699/problem/D D. Fix a Tree time limit per test 2 seconds memory ...

  8. Hdu.1325.Is It A Tree?(并查集)

    Is It A Tree? Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) To ...

  9. HDU 5606 tree 并查集

    tree 把每条边权是1的边断开,发现每个点离他最近的点个数就是他所在的连通块大小. 开一个并查集,每次读到边权是0的边就合并.最后Ans​i​​=size[findset(i)],size表示每个并 ...

随机推荐

  1. java实现4种内部排序

    两种插入类排序: 直接插入排序: public static void insertSort(int[] arr, int len){ for(int i=1; i<len; i++){ int ...

  2. MyBatis 示例-动态 SQL

    MyBatis 的动态 SQL 包括以下几种元素: 详细的使用参考官网文档:http://www.mybatis.org/mybatis-3/zh/dynamic-sql.html 本章内容简单描述这 ...

  3. Java多线程(九):生产者消费者模型

    生产者消费者模型 生产者:生产任务的个体: 消费者:消费任务的个体: 缓冲区:是生产者和消费者之间的媒介,对生产者和消费者解耦. 当 缓冲区元素为满,生产者无法生产,消费者继续消费: 缓冲区元素为空, ...

  4. springboot application.properties配置大全

    springboot application.properties配置大全 官方文档 https://docs.spring.io/spring-boot/docs/current/reference ...

  5. LeetCode 899. Orderly Queue

    899. Orderly Queue(有序队列) 题目: 给出了一个由小写字母组成的字符串 S.然后,我们可以进行任意次数的移动. 在每次移动中,我们选择前 K 个字母中的一个(从左侧开始),将其从原 ...

  6. 【转】js中的原型

    原文链接:https://blog.csdn.net/u012468376/article/details/53121081 一.什么是原型原型是Javascript中的继承的基础,JavaScrip ...

  7. NETGEAR路由器登录不上 重新获取ip

    当NETGEAR路由器更改了"局域网IP配置",或者重启之后,会出现登录不上的情况 释放IP地址 # ipconfig /release 重新获取 # ipconfig /rene ...

  8. mysql 利用 case 批量更新

  9. jumpserver跳板机docker安装小小趟坑

    最近日常运维的时候发现每次登陆服务器都要打开终端目录连接对应的服务器,闲暇的时候还好,运维任务很重的时候才发现这样的玩法很傻,浪费时间且一点儿都跟不上潮流,然后打开githup开始搞起来.docker ...

  10. String特性之 “字符串驻留池”

    1. 字符串驻留池,就是一块与堆区并行的存放字符串对象的内存区,JVM的驻留池机制规定: 在池中创建一个String对象,第二行会先在池中寻找是否有值与"abc"相同的String ...