代码为nkoj1536--【Usaco
Oct08 Gold】奶牛串门(Pasture Walking)
#include<cstdio>
#include<iostream>
#include<algorithm>
#include<cstring>
#include<cstdlib>
#include<cmath>
using namespace std;
int father[10005][50];
int dep[10005];
int n,m=0;
int S;
int root;
struct line{
int from;
int to;
int len;
};
line edge[1000005];
int len[100005];
int last[10005],_next[1000005];
void add_edge(int x,int y,int l){
m++;
edge[m].from=x;
edge[m].to=y;
edge[m].len=l;
_next[m]=last[x];
last[x]=m;
}
bool mark[10005];
void dfs(int x,int fa){
int i,h,v;
father[x][0]=fa;
dep[x]=dep[father[x][0]]+1;
int k=ceil(log(dep[x])/log(2));
for(i=1;i<=k;i++){
father[x][i]=father[father[x][i-1]][i-1];
}
for(h=last[x];h;h=_next[h]){
v=edge[h].to;
if(v==fa)continue;
len[v]=len[x]+edge[h].len;
dfs(v,x);
}
}
void go_up(int &v,int p){
int i;
for(i=0;i<S;i++){
if(p&(1<<i))v=father[v][i];
}
}
int lca(int x,int y){
int i,k;
if(dep[x]<dep[y])swap(x,y);
k=dep[x]-dep[y];
go_up(x,k);
if(x==y)return x;
int s=ceil(log(dep[x])/log(2));
for(i=s;i>=0;i--){
if(father[x][i]!=father[y][i]){
x=father[x][i];
y=father[y][i];
}
}
return father[x][0];
}
int main(){
int m;
cin>>n>>m;
int i,j,k;
S=ceil(log(n)/log(2));
for(i=1;i<n;i++){
int x,y,l;
scanf("%d%d%d",&x,&y,&l);
add_edge(x,y,l);
add_edge(y,x,l);
}
dfs(1,0);
while(m--){
int x,y,t;
scanf("%d%d",&x,&y);
t=lca(x,y);
printf("%d\n",len[x]+len[y]-2*len[t]);
}
}