传送门

题意:

一棵树,多次询问,给出$m$个点,求有几个点到给定点最近


写了一晚上...

当然要建虚树了,但是怎么$DP$啊

大爷题解传送门

我们先求出到虚树上某个点最近的关键点

然后枚举所有的边$(f,x)$,讨论一下边上的点的子树应该靠谁更近

倍增求出分界点

注意有些没出现在虚树上的子树

注意讨论的时候只讨论链上的不包括端点,否则$f$的子树会被贡献多次

学到的一些$trick:$

1.$pair$的妙用

2.不需要建出虚树只要求虚树的$dfs$序(拓扑序)和$fa$就可以$DP$了

注意$DP$的时候必须先用儿子更新父亲再用父亲更新儿子,因为父亲的最优值有可能在其他儿子

  1. #include <iostream>
  2. #include <cstdio>
  3. #include <cstring>
  4. #include <algorithm>
  5. #include <cmath>
  6. using namespace std;
  7. #define pii pair<int,int>
  8. #define MP make_pair
  9. #define fir first
  10. #define sec second
  11. typedef long long ll;
  12. const int N=3e5+,INF=1e9;
  13. inline int read(){
  14. char c=getchar();int x=,f=;
  15. while(c<''||c>''){if(c=='-')f=-;c=getchar();}
  16. while(c>=''&&c<=''){x=x*+c-'';c=getchar();}
  17. return x*f;
  18. }
  19.  
  20. int n,Q;
  21. struct Edge{
  22. int v,ne,w;
  23. }e[N<<];
  24. int cnt,h[N];
  25. inline void ins(int u,int v){
  26. cnt++;
  27. e[cnt].v=v;e[cnt].ne=h[u];h[u]=cnt;
  28. cnt++;
  29. e[cnt].v=u;e[cnt].ne=h[v];h[v]=cnt;
  30. }
  31. int fa[N][],deep[N],dfn[N],dfc,size[N],All;
  32. void dfs(int u){
  33. dfn[u]=++dfc;
  34. size[u]=;
  35. for(int i=;(<<i)<=deep[u];i++)
  36. fa[u][i]=fa[ fa[u][i-] ][i-];
  37. for(int i=h[u];i;i=e[i].ne)
  38. if(e[i].v!=fa[u][]){
  39. fa[e[i].v][]=u;
  40. deep[e[i].v]=deep[u]+;
  41. dfs(e[i].v);
  42. size[u]+=size[e[i].v];
  43. }
  44. }
  45. inline int lca(int x,int y){
  46. if(deep[x]<deep[y]) swap(x,y);
  47. int bin=deep[x]-deep[y];
  48. for(int i=;i>=;i--)
  49. if((<<i)&bin) x=fa[x][i];
  50. for(int i=;i>=;i--)
  51. if(fa[x][i]!=fa[y][i]) x=fa[x][i],y=fa[y][i];
  52. return x==y ? x :fa[x][];
  53. }
  54.  
  55. int a[N],st[N],par[N],dis[N],t[N],m,ans[N];
  56. int remain[N];
  57. inline bool cmp(int x,int y){return dfn[x]<dfn[y];}
  58. inline void ins2(int x,int y){par[y]=x;dis[y]=deep[y]-deep[x];}
  59. pii g[N];
  60. void dp(int m){
  61. for(int i=m;i>;i--){
  62. int x=t[i],f=par[x];
  63. g[f]=min(g[f],MP(g[x].fir+dis[x],g[x].sec));
  64. }
  65. for(int i=;i<=m;i++){
  66. int x=t[i],f=par[x];
  67. g[x]=min(g[x],MP(g[f].fir+dis[x],g[f].sec));
  68. }
  69. }
  70. inline int jump1(int x,int tar){
  71. for(int i=;i>=;i--)
  72. if(deep[ fa[x][i] ]>=tar) x=fa[x][i];
  73. return x;
  74. }
  75. inline int jump(int x,int tar){
  76. int bin=deep[x]-tar;
  77. for(int i=;i>=;i--)
  78. if((<<i)&bin) x=fa[x][i];
  79. return x;
  80. }
  81. int ora[N];
  82. void solve(){
  83. int n=read(),m=;
  84. for(int i=;i<=n;i++)
  85. ora[i]=a[i]=read(),t[++m]=a[i],g[a[i]]=MP(,a[i]);
  86. sort(a+,a++n,cmp);
  87.  
  88. int top=;
  89. for(int i=;i<=n;i++){
  90. if(!top) {st[++top]=a[i];continue;}
  91. int x=a[i],f=lca(x,st[top]);
  92. while(dfn[f]<dfn[st[top]]){
  93. if(dfn[f]>=dfn[st[top-]]){
  94. ins2(f,st[top--]);
  95. if(f!=st[top]) st[++top]=f,t[++m]=f,g[f]=MP(INF,);
  96. break;
  97. }else ins2(st[top-],st[top]),top--;
  98. }
  99. st[++top]=x;
  100. }
  101. while(top>) ins2(st[top-],st[top]),top--;
  102.  
  103. sort(t+,t++m,cmp);
  104. dp(m);
  105. for(int i=;i<=m;i++) remain[t[i]]=size[t[i]];
  106.  
  107. ans[ g[t[]].sec ]+=All-size[t[]];
  108. for(int i=;i<=m;i++){
  109. int x=t[i],f=par[x];par[x]=;
  110. int t=jump(x,deep[f]+);
  111. remain[f]-=size[t];
  112. if(g[x].sec == g[f].sec) ans[ g[x].sec ]+=size[t]-size[x];
  113. else{
  114. int len=g[x].fir + g[f].fir + dis[x], mid=deep[x]-(len/-g[x].fir);
  115. if( !(len&) && g[f].sec<g[x].sec ) mid++;
  116. int y=jump(x,mid);
  117. ans[ g[f].sec ]+=size[t]-size[y];
  118. ans[ g[x].sec ]+=size[y]-size[x];
  119. }
  120. }
  121. for(int i=;i<=m;i++) ans[ g[t[i]].sec ]+=remain[t[i]];
  122. for(int i=;i<=n;i++) printf("%d%c",ans[ora[i]],i==n?'\n':' '),ans[ora[i]]=;
  123. }
  124. int main(){
  125. //freopen("in","r",stdin);
  126. n=read();All=n;
  127. for(int i=;i<n;i++) ins(read(),read());
  128. dfs();
  129. Q=read();
  130. while(Q--) solve();
  131. }

BZOJ 3572: [Hnoi2014]世界树 [虚树 DP 倍增]的更多相关文章

  1. BZOJ 3572 [HNOI2014]世界树 (虚树+DP)

    题面:BZOJ传送门 洛谷传送门 题目大意:略 细节贼多的虚树$DP$ 先考虑只有一次询问的情况 一个节点$x$可能被它子树内的一个到x距离最小的特殊点管辖,还可能被管辖fa[x]的特殊点管辖 跑两次 ...

  2. bzoj 3572: [Hnoi2014]世界树 虚树 && AC500

    3572: [Hnoi2014]世界树 Time Limit: 20 Sec  Memory Limit: 512 MBSubmit: 520  Solved: 300[Submit][Status] ...

  3. BZOJ 3572: [Hnoi2014]世界树 虚树 树形dp

    https://www.lydsy.com/JudgeOnline/problem.php?id=3572 http://hzwer.com/6804.html 写的时候参考了hzwer的代码,不会写 ...

  4. bzoj3572[Hnoi2014] 世界树 虚树+dp+倍增

    [Hnoi2014]世界树 Time Limit: 20 Sec  Memory Limit: 512 MBSubmit: 1921  Solved: 1019[Submit][Status][Dis ...

  5. bzoj 3572 [Hnoi2014]世界树——虚树

    题目:https://www.lydsy.com/JudgeOnline/problem.php?id=3572 关于虚树:https://www.cnblogs.com/zzqsblog/p/556 ...

  6. bzoj 3572: [Hnoi2014]世界树 虚树

    题目: Description 世界树是一棵无比巨大的树,它伸出的枝干构成了整个世界.在这里,生存着各种各样的种族和生灵,他们共同信奉着绝对公正公平的女神艾莉森,在他们的信条里,公平是使世界树能够生生 ...

  7. 【BZOJ】3572: [Hnoi2014]世界树 虚树+倍增

    [题意]给定n个点的树,m次询问,每次给定ki个特殊点,一个点会被最近的特殊点控制,询问每个特殊点控制多少点.n,m,Σki<=300000. [算法]虚树+倍增 [题解]★参考:thy_asd ...

  8. 洛谷 P3233 [HNOI2014]世界树(虚树+dp)

    题面 luogu 题解 数据范围已经告诉我们是虚树了,考虑如何在虚树上面\(dp\) 以下摘自hzwer博客: 构建虚树以后两遍dp处理出虚树上每个点最近的议事处 然后枚举虚树上每一条边,考虑其对两端 ...

  9. BZOJ 3572: [Hnoi2014]世界树

    BZOJ 3572: [Hnoi2014]世界树 标签(空格分隔): OI-BZOJ OI-虚数 OI-树形dp OI-倍增 Time Limit: 20 Sec Memory Limit: 512 ...

随机推荐

  1. window下部署Solr

    主要步骤如下: 1.下载solr-4.7.2.zip;下载地址:http://archive.apache.org/dist/lucene/java/ 2.解压缩solr-4.7.2.zip,解压后目 ...

  2. 在jquery中防止ajax重复提交

  3. [学习OpenCV攻略][007][缩小图片]

    cvPryDown(输入图片,输出图片) 根据输出图片的大小,把输入图片进行压缩 cvPryUp(输入图片,输出图片) 根据输出图片的大小,把输入图片进行放大 #include "cv.h& ...

  4. 一步一步从原理跟我学邮件收取及发送 5.C语言的socket示例

    说到 C 语言版本的程序,首先要解决的问题就是兼容性. 作为 20 年开发有 10 多年是在服务端的程序员,我深刻地感受到服务端平台的两极分化之严重,linux 派对 windows 那是超级的不屑一 ...

  5. Netty 拆包粘包和服务启动流程分析

    Netty 拆包粘包和服务启动流程分析 通过本章学习,笔者希望你能掌握EventLoopGroup的工作流程,ServerBootstrap的启动流程,ChannelPipeline是如何操作管理Ch ...

  6. jquery checkbox 全选反选代码只能执行一遍,第二次就失败

    遇到问题背景: 在写到购物车的全选交互的时候,商品选中的状态只有在第一次的时候可以,第二次就无法选中:(代码如下) $(".chooseall").click(function() ...

  7. scrapy_ItemLoader

    什么是Itemloader? 一种容器,实现直白高效字段提取 直接赋值取值的方式,会出现一下几个问题 代码量一多,各种css和xpath选择器,充斥整个代码逻辑,没有规则,不利于维护 对于一个字段的预 ...

  8. Node.js之事件监听和发送

    演示事件的发送和监听 const events = require("events"); function Account() { this.balance = 0; events ...

  9. GPU 实现 RGB -- YUV 转换 (OpenGL)

    GPU 实现 RGB -- YUV 转换 前言 RGB --> YUV 转换的公式是现成的,直接在 CPU 端转换的话,只需要遍历每个像素,得到新的 YUV 值,根据其内存分布规律,合理安排分布 ...

  10. 自己写的一个tomcat发布脚本

    闲来无事,就自己写一个shell脚本,方便自己以后在服务器上部署tomcat下的项目.我本地用maven打包,然后每次都要人工去切换一堆堆目录,有点繁琐,所以我写了下面的shell脚本. #! /bi ...