树链剖分

先来LCA的:

 1 #include<iostream>
 2 #include<cstdio>
 3 #include<cmath>
 4 #include<algorithm>
 5 using namespace std;
 6 const int maxn=200000+10;
 7 struct Tedge{int x,y,next;}adj[maxn*2];int fch[maxn],ms=0;
 8 void AddEdge(int u,int v){
 9     adj[++ms]=(Tedge){u,v,fch[u]};fch[u]=ms; adj[++ms]=(Tedge){v,u,fch[v]};fch[v]=ms; return;
10 }
11 int s[maxn],top[maxn],fa[maxn],son[maxn],dep[maxn],n,m;
12 void First_DFS(int x){
13     dep[x]=dep[fa[x]]+1;s[x]=1;
14     for(int i=fch[x];i;i=adj[i].next){
15         int v=adj[i].y;if(v==fa[x]) continue;
16         fa[v]=x;First_DFS(v);
17         if(s[son[x]]<s[v]) son[x]=v;s[x]+=s[v];
18     } return ;
19 }
20 void Second_DFS(int x,int tp){
21     top[x]=tp;
22     if(son[x]) Second_DFS(son[x],tp);
23     for(int i=fch[x];i;i=adj[i].next){
24         int v=adj[i].y;if(v==fa[x]||v==son[x]) continue;
25         Second_DFS(v,v);
26     } return ;
27 }
28 void LCA(int& a, int& b){
29     int f1=top[a],f2=top[b];
30     while(f1!=f2){
31         if(dep[f1]<dep[f2]) swap(a,b),swap(f1,f2);
32         a=fa[f1]; f1=top[a];
33     } return ;
34 }
35 int dist(int a,int b){
36     int ans=dep[a]+dep[b];LCA(a,b);return ans-min(dep[a],dep[b])*2;
37 }
38 inline int read(){
39     int x=0,sig=1;char ch=getchar();
40     while(!isdigit(ch)){if(ch=='-') sig=-1;ch=getchar();}
41     while(isdigit(ch)) x=10*x+ch-'0',ch=getchar();
42     return x*=sig;
43 }
44 inline void write(int x){
45     if(x==0){putchar('0');return;} if(x<0) putchar('-'),x=-x;
46     int len=0,buf[15]; while(x) buf[len++]=x%10,x/=10;
47     for(int i=len-1;i>=0;i--) putchar(buf[i]+'0');return;
48 }
49 void init(){
50     n=read();m=read();for(int i=2;i<=n;i++) AddEdge(read(),read());
51     First_DFS(1);Second_DFS(1,1);return;
52 }
53 void work(){
54     int a,b,c,d[3];
55     while(m--){
56         a=read();b=read();c=read();
57         d[0]=dist(a,b);d[1]=dist(b,c);d[2]=dist(a,c);
58         sort(d,d+3);write(d[1]);putchar('
');
59     } return;
60 }
61 void print(){
62     return;
63 }
64 int main(){
65     init(); work(); print(); return 0;
66 }
原文地址:https://www.cnblogs.com/chxer/p/4430370.html