爱之箭发射(las)

目描述

小海是弓道部的成员,非常擅长射箭(Love Arrow Shoot)。今天弓道部的练习是要射一棵树。一棵树是一个nn个点n−1n−1条边的无向图,且这棵树的第ii个点有一个值wiwi,wi∈[1,m]wi∈[1,m]。每一次小海会射中树的一条边,并将这条边移除。此外,小海定义一棵树的las值为∑vi∗i∑vi∗i,vivi为这棵树中第ii小的wiwi。现在小海会告诉你她射中的边的顺序,你需要回答每一次她射中的边所在的树的las值,之后被射中的边会被移除。答案mod998244353mod998244353

输入

第一行两个数n,mn,m

第二行nn个数wiwi

接下来n−1n−1行每行两个数ai,biai,bi,表示初始的树第ii条边连接aiai和bibi。

接下来n−1n−1行每行一个数表示射中的边。

输出

n-1行每行一个数表示射中的边的树的las值

样例输入

  1. 5 4396
  2. 2 3 1 4 5
  3. 1 2
  4. 1 3
  5. 2 4
  6. 2 5
  7. 4
  8. 1
  9. 2
  10. 3

样例输出

  1. 55
  2. 30
  3. 5
  4. 11

提示

数据范围

前20% n<=1e3

另外20% m<=10

另外20% 保证第i条边连接i和i+1

另外20% n<=1e5

100% n<=5e5 wi<=m<=1e4

下发一个样例满足第一个部分分。

来源

noip2018模拟-robinliu


solution

把操作倒过来,看成加边。

对于每个连通块可以用一棵值域线段树维护每个值出现的次数,值的和,还有la值。

合并时,新的la值可以由值的和*之前的值出现的次数得到。

比如 1*1+2*2+3*3  +2*(1+2+3) -> 3*1+4*2+5*3

线段树合并维护即可

注意x,y均没有左右儿子的特殊情况

  1. #include<cstdio>
  2. #include<iostream>
  3. #include<cstdlib>
  4. #include<cstring>
  5. #include<algorithm>
  6. #include<cmath>
  7. #define maxn 500005
  8. #define mod 998244353
  9. #define ll long long
  10. using namespace std;
  11. int n,m,st[maxn],ed[maxn],w[maxn],id[maxn];
  12. int fa[maxn],root[maxn*18],tot;
  13. int ls[maxn*18],rs[maxn*18],num[maxn*18];
  14. ll ans[maxn],sum[maxn*18],s[maxn*18];
  15. void build(int &k,int l,int r,int pl){
  16. if(!k)k=++tot;
  17. if(l==r){
  18. num[k]=1;sum[k]=s[k]=pl;
  19. return;
  20. }
  21. int mid=l+r>>1;
  22. if(pl<=mid)build(ls[k],l,mid,pl);
  23. else build(rs[k],mid+1,r,pl);
  24. num[k]=num[ls[k]]+num[rs[k]];
  25. sum[k]=sum[ls[k]]+sum[rs[k]];
  26. s[k]=s[ls[k]]+s[rs[k]];
  27. }
  28. int getf(int k){
  29. if(fa[k]==k)return k;
  30. fa[k]=getf(fa[k]);return fa[k];
  31. }
  32. int merge(int x,int y,int la){
  33. if(!x||!y){
  34. return x+y;
  35. }
  36. ls[x]=merge(ls[x],ls[y],la);
  37. rs[x]=merge(rs[x],rs[y],la+num[ls[x]]);
  38. //printf("x:%d y:%d sumx:%d sumy:%d la:%d\n ls:%d %d %d rs:%d %d %d\n",x,y,sum[x],sum[y],la,sum[ls[x]],num[ls[x]],s[ls[x]],sum[rs[x]],num[rs[x]],s[rs[x]]);
  39. if(!ls[x]&&!rs[x]){
  40. sum[x]=sum[x]+sum[y]+(num[x]*s[y])%mod;sum[x]%=mod;
  41. num[x]=num[x]+num[y];s[x]=s[x]+s[y];
  42. return x;
  43. }
  44. sum[x]=sum[ls[x]]+sum[rs[x]]+(num[ls[x]]*s[rs[x]])%mod;sum[x]%=mod;
  45. num[x]=num[ls[x]]+num[rs[x]];
  46. s[x]=s[ls[x]]+s[rs[x]];
  47. //cout<<sum[x]<<' '<<num[x]<<endl;
  48. return x;
  49. }
  50. int main(){
  51. cin>>n>>m;
  52. for(int i=1;i<=n;i++){
  53. scanf("%d",&w[i]);
  54. fa[i]=i;build(root[i],1,m,w[i]);
  55. }
  56. for(int i=1;i<n;i++){
  57. scanf("%d%d",&st[i],&ed[i]);
  58. }
  59. for(int i=1;i<n;i++)scanf("%d",&id[i]);
  60. for(int i=n-1;i>=1;i--){
  61. int x=getf(st[id[i]]),y=getf(ed[id[i]]);
  62. //cout<<"---------\n";
  63. //cout<<x<<' '<<y<<endl;
  64. root[x]=merge(root[x],root[y],0);
  65. ans[i]=sum[root[x]];
  66. fa[y]=x;
  67. }
  68. for(int i=1;i<n;i++)printf("%lld\n",ans[i]);
  69. return 0;
  70. }
  71. /*
  72. 5 5
  73. 2 2 1 4 5
  74. 1 2
  75. 1 3
  76. 2 4
  77. 2 5
  78. 4
  79. 1
  80. 2
  81. 3
  82. */

爱之箭发射(las)的更多相关文章

  1. 贪心:leetcode 870. Advantage Shuffle、134. Gas Station、452. Minimum Number of Arrows to Burst Balloons、316. Remove Duplicate Letters

    870. Advantage Shuffle 思路:A数组的最大值大于B的最大值,就拿这个A跟B比较:如果不大于,就拿最小值跟B比较 A可以改变顺序,但B的顺序不能改变,只能通过容器来获得由大到小的顺 ...

  2. LiDAR、LAS、LAS Dataset与点云

    LiDAR Light Detection And Ranging,激光探测及测距,是一种光学遥感技术,使用激光对地球表面的密集采样,产生高精度X.Y.Z测量值. 激光雷达系统的主要硬件组成部分包括一 ...

  3. [LeetCode] 452. Minimum Number of Arrows to Burst Balloons 最少箭数爆气球

    There are a number of spherical balloons spread in two-dimensional space. For each balloon, provided ...

  4. [LeetCode] Minimum Number of Arrows to Burst Balloons 最少数量的箭引爆气球

    There are a number of spherical balloons spread in two-dimensional space. For each balloon, provided ...

  5. pyqt 发射接收信号

    翻页控件: 一.定义并发射信号: #!/usr/bin/python # #coding=utf-8 # __author__='' from PyQt4.QtCore import * from P ...

  6. Unity3D 5.x 简单实例 - 发射炮弹

    1,下载.安装: http://unity3d.com/cn/get-unity/download/archive 建议直接借助 UnityDownloadAssistant 进行安装,根据需要勾选需 ...

  7. cc1101 ASK发射模式

    cc1101 配置  433.919830Mhz  1.19948kBaud   199.951172  58.035714 #ifndef _CC1100_H_#define _CC1100_H_ ...

  8. 关于粒子发射(CAEmitterLayer)

    技术是条长而远的路,只有不断学习丰富自己的技能才能让自己行走在路上! CAEmitterCell CAEmitterCell: CAEmitterCell是粒子发射系统里的粒子,用CAEmitterC ...

  9. (视频)《快速创建网站》 4.2 完结篇 – 应用运营vs.发射卫星,遥测(Telemetry) 技术

    本文是<快速创建网站>系列的第10篇(完结篇),如果你还没有看过之前的内容,建议你点击以下目录中的章节先阅读其他内容再回到本文.访问本系列目录,请点击:http://devopshub.c ...

随机推荐

  1. 求最大公约数和最小公倍数_python

    """写两个函数,分别求两个整数的最大公约数和最小公倍数,调用这两个函数,并输出结果.两个整数由键盘输入.""" ''' 设两个整数u和v, ...

  2. C#进阶之全面解析Lambda表达式

    引言 在实际的项目中遇到一个问题,我们经常在网上搜索复制粘贴,其中有些代码看着非常的简洁,比如Lambda表达式,但是一直没有去深入了解它的由来,以及具体的使用方法,所以在使用的时候比较模糊,其次,编 ...

  3. 驾考试题的json代码

    { "statusCode": "000000", "desc": "请求成功", "result" ...

  4. Centos7 PHP的安装和配置

    前面Nginx和httpd的安装都是为了支持PHP而弄的,然后这个目标就给了我一沉重的打击,等我慢慢道来,先来说说PHP的安装和配置吧. 一.PHP的安装 1.由于linux的yum源不存在php7. ...

  5. Python 正则表达式 匹配任意字符

    .(句点)匹配除了换行之外的所有一个字符, .*(点-星)匹配除了换行外的所有字符 >>> >>> r=re.compile(r'.*')>>> ...

  6. hibernate的get() load() 和find()区别

    如果找不到符合条件的纪录,get()方法将返回null.如果找不到符合条件的纪录,find()方法将返回null.如果找不到符合 条件的纪录,load()将会报出ObjectNotFoundEccep ...

  7. static关键字 详解

    原文地址:http://blog.csdn.net/keyeagle/article/details/6708077 google了近三页的关于C语言中static的内容,发现可用的信息很少,要么长篇 ...

  8. ACM二分搜索中的最大化最小值 总结

    这类题目都有个相似的地方就是需要你去找一个临界点. 分析题目要你求什么,例如时间 那么mid就是时间 看求得这个跟什么相关 例如 poj 3258 求得是距离 这个距离跟两者之间的差相关 那题目要求你 ...

  9. CQRS之旅——旅程5(准备发布V1版本)

    旅程5:准备发布V1版本 添加功能和重构,为V1版本发布做准备. "大多数人在完成一件事之后,就像留声机的唱片一样,一遍又一遍地使用它,直到它破碎,忘记了过去是用来创造更多未来的东西.&qu ...

  10. 申请社交平台appkey详细教程

    申请社交平台appkey详细教程 大部分app都需要实现分享到微信.微博等社交平台的功能,但是在各个平台上申请appkey是一件很繁琐的事情.现在来分享一个申请社交平台appkey详细教程,在开发过程 ...