[BZO3572][HNOI2014]世界树:虚树+倍增
分析
思维难度几乎为\(0\)的虚树码农(并不)题。
代码
#include <bits/stdc++.h>
#define rin(i,a,b) for(register int i=(a);i<=(b);++i)
#define irin(i,a,b) for(register int i=(a);i>=(b);--i)
#define trav(i,a) for(register int i=head[a];i;i=e[i].nxt)
#define itrav(i,a) for(register int i=ihead[a];i;i=ie[i].nxt)
typedef long long LL;
using std::cin;
using std::cout;
using std::endl;
inline int read(){
int x=0,f=1;char ch=getchar();
while(!isdigit(ch)){if(ch=='-')f=-1;ch=getchar();}
while(isdigit(ch)){x=x*10+ch-'0';ch=getchar();}
return x*f;
}
const int MAXN=3e5+5;
int n,q,ecnt,head[MAXN];
int tot,id[MAXN],num[MAXN],len,st[MAXN<<1][21],pos[MAXN];
int dep[MAXN],siz[MAXN],anc[MAXN][21];
int m,mm,h[MAXN<<1],hh[MAXN],top,sta[MAXN];
int iecnt,ihead[MAXN];
int ans[MAXN];
bool isc[MAXN];
struct Edge{
int to,nxt;
}e[MAXN<<1];
inline void add_edge(int bg,int ed){
++ecnt;
e[ecnt].to=ed;
e[ecnt].nxt=head[bg];
head[bg]=ecnt;
}
void dfs1(int x,int pre,int depth){
id[x]=++tot;
num[tot]=x;
st[++len][0]=id[x];
pos[x]=len;
dep[x]=depth;
siz[x]=1;
anc[x][0]=pre;
trav(i,x){
int ver=e[i].to;
if(ver==pre) continue;
dfs1(ver,x,depth+1);
st[++len][0]=id[x];
siz[x]+=siz[ver];
}
}
void buildst(){
int lim=log2(len);
rin(i,1,lim) rin(j,1,len-(1<<i)+1)
st[j][i]=std::min(st[j][i-1],st[j+(1<<(i-1))][i-1]);
}
void buildanc(){
rin(i,1,20) rin(j,1,n)
anc[j][i]=anc[anc[j][i-1]][i-1];
}
inline int lca(int x,int y){
x=pos[x],y=pos[y];
if(x>y) std::swap(x,y);
int lim=log2(y-x+1);
return num[std::min(st[x][lim],st[y-(1<<lim)+1][lim])];
}
inline bool cmp(int x,int y){
return id[x]<id[y];
}
struct iedge{
int to,nxt;
}ie[MAXN];
inline void add_iedge(int bg,int ed){
++iecnt;
ie[iecnt].to=ed;
ie[iecnt].nxt=ihead[bg];
ihead[bg]=iecnt;
}
void build_itree(){
std::sort(h+1,h+m+1,cmp);
rin(i,2,mm) h[++m]=lca(h[i-1],h[i]);
h[++m]=1;
std::sort(h+1,h+m+1,cmp);
m=std::unique(h+1,h+m+1)-h-1;
top=0;
rin(i,1,m){
while(top&&id[h[i]]>id[sta[top]]+siz[sta[top]]-1) add_iedge(sta[top-1],sta[top]),--top;
sta[++top]=h[i];
}
while(top>1) add_iedge(sta[top-1],sta[top]),--top;
--top;
}
struct ctrl{
int pos,dis;
inline friend bool operator < (ctrl A,ctrl B){
return A.dis==B.dis?A.pos<B.pos:A.dis<B.dis;
}
}c[MAXN];
void dfs2(int x){
if(isc[x]) c[x]=(ctrl){x,0};
else c[x]=(ctrl){0,(int)1e9};
itrav(i,x){
int ver=ie[i].to;
dfs2(ver);
c[x]=std::min(c[x],(ctrl){c[ver].pos,c[ver].dis+dep[ver]-dep[x]});
}
}
void dfs3(int x,int pre){
if(pre) c[x]=std::min(c[x],(ctrl){c[pre].pos,c[pre].dis+dep[x]-dep[pre]});
itrav(i,x){
int ver=ie[i].to;
dfs3(ver,x);
}
}
inline int getveranc(int x,int pre){
int ret=x;
irin(i,20,0)
if(dep[anc[ret][i]]>dep[pre])
ret=anc[ret][i];
return ret;
}
inline int climb(int x,int y){
int ret=x,tt=0;
while(y){
if(y&1) ret=anc[ret][tt];
++tt;
y>>=1;
}
return ret;
}
void dfs4(int x,int pre){
ans[c[x].pos]+=siz[x];
itrav(i,x){
int ver=ie[i].to,veranc=getveranc(ver,x);
dfs4(ver,x);
ans[c[x].pos]-=siz[veranc];
if(c[x].pos==c[ver].pos)
ans[c[x].pos]+=siz[veranc]-siz[ver];
else{
int mid=0;
if((dep[ver]-dep[x]+c[ver].dis-c[x].dis)&1) mid=dep[ver]-(((dep[x]+dep[ver]+c[ver].dis-c[x].dis)>>1)+1);
else if(c[x].pos<c[ver].pos) mid=dep[ver]-(((dep[x]+dep[ver]+c[ver].dis-c[x].dis)>>1)+1);
else mid=dep[ver]-((dep[x]+dep[ver]+c[ver].dis-c[x].dis)>>1);
mid=climb(ver,mid);
ans[c[x].pos]+=siz[veranc]-siz[mid];
ans[c[ver].pos]+=siz[mid]-siz[ver];
}
}
}
/*
const int MAXN=3e5+5;
int n,q,ecnt,head[MAXN];
int tot,id[MAXN],num[MAXN],len,st[MAXN<<1][21],pos[MAXN];
int dep[MAXN],siz[MAXN],anc[MAXN][21];
int m,mm,h[MAXN<<1],hh[MAXN],top,sta[MAXN];
int iecnt,ihead[MAXN];
int ans[MAXN];
bool isc[MAXN];
*/
void clear_itree(){
iecnt=0;
rin(i,1,m) ihead[h[i]]=ans[h[i]]=0,isc[h[i]]=false;
}
int main(){
n=read();
rin(i,2,n){
int u=read(),v=read();
add_edge(u,v);
add_edge(v,u);
}
dfs1(1,0,1);
buildst();
buildanc();
q=read();
while(q--){
m=mm=read();
rin(i,1,m) h[i]=hh[i]=read(),isc[h[i]]=true;
build_itree();
dfs2(1);
dfs3(1,0);
dfs4(1,0);
rin(i,1,mm) printf("%d ",ans[hh[i]]);
putchar('\n');
clear_itree();
}
return 0;
}
[BZO3572][HNOI2014]世界树:虚树+倍增的更多相关文章
- 【BZOJ】3572: [Hnoi2014]世界树 虚树+倍增
[题意]给定n个点的树,m次询问,每次给定ki个特殊点,一个点会被最近的特殊点控制,询问每个特殊点控制多少点.n,m,Σki<=300000. [算法]虚树+倍增 [题解]★参考:thy_asd ...
- bzoj3572[Hnoi2014] 世界树 虚树+dp+倍增
[Hnoi2014]世界树 Time Limit: 20 Sec Memory Limit: 512 MBSubmit: 1921 Solved: 1019[Submit][Status][Dis ...
- BZOJ 3572: [Hnoi2014]世界树 [虚树 DP 倍增]
传送门 题意: 一棵树,多次询问,给出$m$个点,求有几个点到给定点最近 写了一晚上... 当然要建虚树了,但是怎么$DP$啊 大爷题解传送门 我们先求出到虚树上某个点最近的关键点 然后枚举所有的边$ ...
- 【BZOJ3572】[Hnoi2014]世界树 虚树
[BZOJ3572][Hnoi2014]世界树 Description 世界树是一棵无比巨大的树,它伸出的枝干构成了整个世界.在这里,生存着各种各样的种族和生灵,他们共同信奉着绝对公正公平的女神艾莉森 ...
- bzoj 3572: [Hnoi2014]世界树 虚树 && AC500
3572: [Hnoi2014]世界树 Time Limit: 20 Sec Memory Limit: 512 MBSubmit: 520 Solved: 300[Submit][Status] ...
- bzoj 3572 [Hnoi2014]世界树——虚树
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=3572 关于虚树:https://www.cnblogs.com/zzqsblog/p/556 ...
- BZOJ 3572: [Hnoi2014]世界树 虚树 树形dp
https://www.lydsy.com/JudgeOnline/problem.php?id=3572 http://hzwer.com/6804.html 写的时候参考了hzwer的代码,不会写 ...
- 洛谷 P3233 [HNOI2014]世界树(虚树+dp)
题面 luogu 题解 数据范围已经告诉我们是虚树了,考虑如何在虚树上面\(dp\) 以下摘自hzwer博客: 构建虚树以后两遍dp处理出虚树上每个点最近的议事处 然后枚举虚树上每一条边,考虑其对两端 ...
- bzoj 3572: [Hnoi2014]世界树 虚树
题目: Description 世界树是一棵无比巨大的树,它伸出的枝干构成了整个世界.在这里,生存着各种各样的种族和生灵,他们共同信奉着绝对公正公平的女神艾莉森,在他们的信条里,公平是使世界树能够生生 ...
- BZOJ 3572 [HNOI2014]世界树 (虚树+DP)
题面:BZOJ传送门 洛谷传送门 题目大意:略 细节贼多的虚树$DP$ 先考虑只有一次询问的情况 一个节点$x$可能被它子树内的一个到x距离最小的特殊点管辖,还可能被管辖fa[x]的特殊点管辖 跑两次 ...
随机推荐
- [转帖]「白帽黑客成长记」Windows提权基本原理(上)
「白帽黑客成长记」Windows提权基本原理(上) https://www.cnblogs.com/ichunqiu/p/10949592.html 我们通常认为配置得当的Windows是安全的,事实 ...
- numpy伪随机数的生成
numpy伪随机数的生成 normal函数 可以用normal来得到一个标准正态分布的4×4样本数组 >>> import numpy as np >>> samp ...
- zookeeper核心知识与投票机制详解
Zookeeper数据模型与session机制:zookeeper的数据模型有点类似于文件夹的树状结构,每一个节点都叫做znode,每一个节点都可以有子节点和数据,就好像文件夹下面可以有文件和子文件夹 ...
- 11.jQuery之淡入淡出效果
知识点:fadeIn fadeOut fadeToggle fadeTo <style> div { width: 150px; height: 300px; background ...
- Jquery复习(四)之text()、html()、val()
三个简单实用的用于 DOM 操作的 jQuery 方法: text() - 设置或返回所选元素的文本内容 html() - 设置或返回所选元素的内容(包括 HTML 标记) val() - 设置或返回 ...
- J2EE WEB应用架构分析
1. 架构概述 J2EE体系包括java server pages(JSP) ,java SERVLET, enterprise bean,WEB service等技术.这些技术的出现给电子商务时代的 ...
- vue与react对比
相同点 1.都使用 virtual DOM 2.都是组件化开发 or 都提供了组件化的视图组件 3.数据的改变会引起视图的二次渲染 4.都只有骨架,其他的功能如路由.状态管理等是框架分离的组件. 5. ...
- angular集成tinymce
1.前言 我使用的是angular的7.x版本,和之前的低版本集成方式有所区别.这里记录下基本的集成步骤. 2.集成步骤 2.1安装tinymac包 npm install tinymce --sav ...
- nginx的简单介绍
nginx简单介绍 Nginx的负载均衡策略可以分两大类:内置策略和扩展侧略: 内置策略包括:轮询,加权轮询,IP hash 扩展策略是:url hash ,fair nginx.conf文件结构 1 ...
- Instr()函数用法
返回 Variant (Long),指定一字符串在另一字符串中最先出现的位置. 语法 InStr([start, ]string1, string2[, compare]) InStr 函数的语法具有 ...