[LNOI2014]LCA(树链剖分)
题目:给你一棵树,给你n个询问,每个询问要求输出$\sum_{i=l}^{r}depth(LCA(i,z))$
细看看其实没有想象的那么难
大体思路:
1、对于每个询问,考虑打差分变成$\sum_{i=0}^{r}depth(LCA(i,z))-\sum_{i=0}^{l-1}depth(LCA(i,z))$
2、那么这里就是一个思考点了
如何表示$\sum_{i=0}^{p}depth(LCA(i,z))$?
我也不知道
这种时候就该换一个角度思考了
啥是深度?
不就是从根到他有几个点嘛
对于两个点i,j
从i向根的路径上+1
那么$query(root,j)$就是要求的$dep(LCA(i,j))$了
到这里思路就差不多出来了
①把每个询问分成两个,打差分
②排序询问,逐个插入$add(i,root,1)$
③每个询问查出$query(z,root)$
好了答案出来了
#include<cstdio> #include<algorithm> using std::sort; #define mo 201314 )%mo;} int n,m; struct sumireko { int to,ne; }e[]; ],ecnt; void addline(int f,int t) { e[++ecnt].to=t; e[ecnt].ne=he[f]; he[f]=ecnt; } ],hop[],size[],dson[],llen[],dep[],idn[],idnar; void dfs1(int x) { size[x]=; ; for(int i=he[x],t;i;i=e[i].ne) { t=e[i].to; dfs1(t); size[x]+=size[t]; if(lin<size[t]) { lin=size[t]; dson[x]=t; } } } void dfs2(int x,int top) { idn[x]=++idnar; hop[x]=top; llen[top]++; if(!dson[x]) return; dfs2(dson[x],top); for(int i=he[x],t;i;i=e[i].ne) { t=e[i].to; if(t==dson[x]) continue; dfs2(t,t); } } struct usami { int f,id,r,z; void set(int u,int i,int o,int p){f=u,id=i,r=o,z=p;} bool friend operator < (usami a,usami b) { return a.r<b.r; } }qqq[]; int qcnt; ]; struct segtree { ],del[],size[]; void build(int px,int pl,int pr) { if(pl==pr) { size[px]=; return; } ; build(px<<,pl,mid); build(px<<|,mid+,pr); size[px]=size[px<<]+size[px<<|]; } void fuckup(int px,int pl,int pr) { if(pl==pr) return; v[px]=v[px<<]+v[px<<|]; MOD(v[px]); } void fuckdown(int px,int pl,int pr) { if(pl==pr) return; if(del[px]) { v[px<<]+=del[px]*size[px<<];MOD(v[px<<]); del[px<<]+=del[px];MOD(del[px<<]); v[px<<|]+=del[px]*size[px<<|];MOD(v[px<<|]); del[px<<|]+=del[px];MOD(del[px<<|]); del[px]=; } } void add(int px,int pl,int pr,int vin,int ql,int qr) { if(ql<=pl&&qr>=pr) { v[px]+=vin*size[px]; del[px]+=vin; MOD(v[px]); MOD(del[px]); return; } fuckdown(px,pl,pr); ; ,pl,mid,vin,ql,qr); |,mid+,pr,vin,ql,qr); fuckup(px,pl,pr); } int query(int px,int pl,int pr,int ql,int qr) { if(ql<=pl&&qr>=pr) return v[px]; fuckdown(px,pl,pr); ; ; ,pl,mid,ql,qr),MOD(ret); |,mid+,pr,ql,qr),MOD(ret); return ret; } }tr; void inp(int x) { ]) { tr.add(,,n,,idn[hop[x]],idn[x]); x=fa[hop[x]]; } tr.add(,,n,,idn[],idn[x]); } void qq(int x,int id,int f) { ; ]) { prt+=tr.query(,,n,idn[hop[x]],idn[x]); MOD(prt); x=fa[hop[x]]; } prt+=tr.query(,,n,idn[],idn[x]); MOD(prt); ans[id]+=f*prt; MOD(ans[id]); } int main() { scanf("%d%d",&n,&m); ;i<n;i++) scanf("%d",&fa[i]),addline(fa[i],i); dep[]=; dfs1(); dfs2(,); tr.build(,,n); ,lin,rin,zin;i<=m;i++) { scanf("%d%d%d",&lin,&rin,&zin); qqq[++qcnt].,i,lin-,zin); qqq[++qcnt].,i,rin,zin); } sort(qqq+,qqq+qcnt+); ; ;i<=qcnt;i++) { while(tinar<qqq[i].r) {tinar++;inp(tinar);} qq(qqq[i].z,qqq[i].id,qqq[i].f); } ;i<=m;i++) printf("%d\n",ans[i]); ; }
精污代码慎入
[LNOI2014]LCA(树链剖分)的更多相关文章
- [BZOJ3626] [LNOI2014]LCA(树链剖分)
[BZOJ3626] [LNOI2014]LCA(树链剖分) 题面 给出一棵N个点的树,要求支持Q次询问,每次询问一个点z与编号为区间[l,r]内的点分别求最近公共祖先得到的最近公共祖先深度和.N, ...
- BZOJ 3626: [LNOI2014]LCA [树链剖分 离线|主席树]
3626: [LNOI2014]LCA Time Limit: 10 Sec Memory Limit: 128 MBSubmit: 2050 Solved: 817[Submit][Status ...
- BZOJ 3626: [LNOI2014]LCA( 树链剖分 + 离线 )
说多了都是泪啊...调了这么久.. 离线可以搞 , 树链剖分就OK了... -------------------------------------------------------------- ...
- BZOJ3626[LNOI2014]LCA——树链剖分+线段树
题目描述 给出一个n个节点的有根树(编号为0到n-1,根节点为0).一个点的深度定义为这个节点到根的距离+1.设dep[i]表示点i的深度,LCA(i,j)表示i与j的最近公共祖先.有q次询问,每次询 ...
- bzoj 3626 : [LNOI2014]LCA (树链剖分+线段树)
Description 给出一个n个节点的有根树(编号为0到n-1,根节点为0).一个点的深度定义为这个节点到根的距离+1.设dep[i]表示点i的深度,LCA(i,j)表示i与j的最近公共祖先.有q ...
- 【bzoj3626】[LNOI2014]LCA 树链剖分+线段树
题目描述 给出一个n个节点的有根树(编号为0到n-1,根节点为0).一个点的深度定义为这个节点到根的距离+1.设dep[i]表示点i的深度,LCA(i,j)表示i与j的最近公共祖先.有q次询问,每次询 ...
- BZOJ 3626: [LNOI2014]LCA 树链剖分 线段树 离线
http://www.lydsy.com/JudgeOnline/problem.php?id=3626 LNOI的树链剖分题没有HAOI那么水,学到的东西还是很多的. 我如果现场写,很难想出来这种题 ...
- BZOJ 3626 [LNOI2014]LCA ——树链剖分
思路转化很巧妙. 首先把询问做差分. 然后发现加入一个点就把路径上的点都+1,询问的时候直接询问到根的路径和. 这样和原问题是等价的,然后树链剖分+线段树就可以做了. #include <map ...
- bzoj3626 [LNOI2014]LCA——树链剖分
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=3626 思路很巧妙,把区间换成前缀和相减: 把 l ~ r 到根路径上的点的点权都+1,然后 ...
- 洛谷 P4211 [LNOI2014]LCA (树链剖分+离线)
题目:https://www.luogu.org/problemnew/solution/P4211 相当难的一道题,其思想难以用言语表达透彻. 对于每个查询,区间[L,R]中的每个点与z的lca肯定 ...
随机推荐
- Ubuntu利用TCP协议来获取server时间
Linux利用TCP协议来获取server时间 这里使用Unix网络编程里面的一个小程序,该client建立一个到server的TCP连接,然后读取由server以直观可读格式简单地送回的当前时间和日 ...
- fatal error LNK1123: failure during conversion to COFF: file invalid or corrupt
project->xx Properties->Manifest->Input and Output->Embed Manifest将yes修改为no
- uclibc,eglibc,glibc之间的区别和联系【转】
本文转载自:https://www.crifan.com/relation_between_uclibc_glibc_eglibc/ [glibc,uclibc,eglibc的简介] 1.Glibc ...
- HTTPS数据包抓取的可行性分析
HTTPS数据包抓取的可行性分析 相信只要是从事软件开发, 多多少少都会涉及到数据包的抓取.常见的有网页数据抓取(即网页爬虫),应用程序数据包抓取等.网页数据抓取比较简单, 在chrome下可以非常方 ...
- SPOJ OTOCI 动态树 LCT
SPOJ OTOCI 裸的动态树问题. 回顾一下我们对树的认识. 最初,它是一个连通的无向的无环的图,然后我们发现由一个根出发进行BFS 会出现层次分明的树状图形. 然后根据树的递归和层次性质,我们得 ...
- Asp.Net 文件下载1——流下载(适用于大文件且防盗链)(转)
使用流防盗链下载大文件 直接上 Asp.net 后置代码好了 using System; using System.Data; using System.Configuration; using Sy ...
- 分享几篇有关react-native的博客
http://segmentfault.com/a/1190000002646155 http://facebook.github.io/react-native/docs/native-module ...
- BFS POJ 2251 Dungeon Master
题目传送门 /* BFS:这题很有意思,像是地下城,图是立体的,可以从上张图到下一张图的对应位置,那么也就是三维搜索,多了z坐标轴 */ #include <cstdio> #includ ...
- jquery实现文字自动向上滚动,鼠标放上去停止,移开继续滚动代码...
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...
- 面向过程与面向对象引入三大特性&&事务
1.面向过程 int a = 10;int b =5;int c = a+b; int r1 = 10;int r2 = 5;double c = r1*r1*3.14 - r2*r2*3.14 缺点 ...