博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
BZOJ 3572 世界树(虚树)
阅读量:6984 次
发布时间:2019-06-27

本文共 2484 字,大约阅读时间需要 8 分钟。

http://www.lydsy.com/JudgeOnline/problem.php?id=3572

思路:建立虚树,然后可以发现,每条边不是同归属于一端,那就是切开,一半给上面,一半给下面。

1 #include
2 #include
3 #include
4 #include
5 #include
6 #define N 300005 7 int tot,go[N*2],next[N*2],first[N],sz,deep[N],tmp[N],tree[N]; 8 int son[N],dfn[N],fa[N][20],bin[20],ask[N],In[N],st[N],n,m,ans[N]; 9 int father[N],val[N]; 10 std::pair
near[N]; 11 int read(){ 12 int t=0,f=1;char ch=getchar(); 13 while (ch<'0'||ch>'9'){ if (ch=='-') f=-1;ch=getchar();} 14 while ('0'<=ch&&ch<='9'){t=t*10+ch-'0';ch=getchar();} 15 return t*f; 16 } 17 void insert(int x,int y){ 18 tot++; 19 go[tot]=y; 20 next[tot]=first[x]; 21 first[x]=tot; 22 } 23 void add(int x,int y){ 24 insert(x,y);insert(y,x); 25 } 26 void dfs(int x){ 27 son[x]=1; 28 dfn[x]=++sz; 29 for (int i=1;i<=19;i++) 30 fa[x][i]=fa[fa[x][i-1]][i-1]; 31 for (int i=first[x];i;i=next[i]){ 32 int pur=go[i]; 33 if (pur==fa[x][0]) continue; 34 deep[pur]=deep[x]+1; 35 fa[pur][0]=x; 36 dfs(pur); 37 son[x]+=son[pur]; 38 } 39 } 40 int find(int x,int dep){ 41 for (int i=19;i>=0;i--) 42 if (deep[fa[x][i]]>=dep) x=fa[x][i]; 43 return x; 44 } 45 int lca(int x,int y){ 46 if (deep[x]
=0;i--) 53 if (fa[x][i]!=fa[y][i]) 54 x=fa[x][i],y=fa[y][i]; 55 return fa[x][0]; 56 } 57 bool cmp(int a,int b){ 58 return dfn[a]
deep[x]){ 76 if (deep[st[top-1]]<=deep[x]){ 77 father[st[top]]=x; 78 } 79 top--; 80 } 81 if (st[top]!=x){ 82 father[x]=st[top];tree[++all]=x; 83 st[++top]=x;near[x]=std::make_pair(1<<30,0); 84 } 85 st[++top]=p; 86 } 87 } 88 std::sort(tree+1,tree+1+all,cmp); 89 for (int i=1;i<=all;i++){ 90 int p=tree[i],f=father[p]; 91 val[p]=son[p]; 92 if (i>1) In[p]=deep[p]-deep[f]; 93 } 94 for (int i=all;i>1;i--){ 95 int p=tree[i],f=father[p]; 96 near[f]=std::min(near[f],std::make_pair(near[p].first+In[p],near[p].second)); 97 } 98 for (int i=2;i<=all;i++){ 99 int p=tree[i],f=father[p];100 near[p]=std::min(near[p],std::make_pair(near[f].first+In[p],near[f].second));101 }102 for (int i=1;i<=all;i++){103 int p=tree[i],f=father[p],sum=son[find(p,deep[f]+1)]-son[p];104 if (f==0) ans[near[p].second]+=n-son[p];105 else{106 val[f]-=sum+son[p];107 if (near[p].second==near[f].second) ans[near[p].second]+=sum;108 else{109 int dis=(deep[p]-deep[f]-near[p].first+near[f].first)/2;110 if (dis+near[p].first==near[f].first+deep[p]-deep[f]-dis&&near[f].second

 

转载于:https://www.cnblogs.com/qzqzgfy/p/5585545.html

你可能感兴趣的文章
iOS开发网络篇—网络请求(HTTP协议)小结(转)
查看>>
navicate连接Linux下mysql慢,卡,以及mysql相关查询,授权
查看>>
Unity 各平台中的路径
查看>>
New Concept English three(21)
查看>>
试卷考试
查看>>
六大赚钱定律,让你赚大钱
查看>>
手写ORM入门篇(一)
查看>>
每天读5分钟,受益匪浅、
查看>>
HTTP学习笔记:HTTP的消息结构
查看>>
queue POJ 2259 Team Queue
查看>>
Codeforces Round #345 (Div. 2)
查看>>
java数组-如何在一堆数据中使用数组!
查看>>
BZOJ5286:[HNOI/AHOI2018]转盘——题解
查看>>
37.Intellij IDEA解决GBK乱码
查看>>
Go语言的多态(Polymorphism)
查看>>
Struts2--DomainModel接收参数---使用广泛!!!
查看>>
如何用cocoapods 来管理项目中的第三方框架?
查看>>
手工成本维护不可以将成本改为零
查看>>
运算符优先级
查看>>
请教 Discuz syscache 中一段cache 的意思
查看>>