这个就比较简单了~
Code:
#include <cstdio>
#include <algorithm>
#define N 100004
#define inf 1000000000
#define setIO(s) freopen(s".in","r",stdin) // , freopen(s".out","w",stdout)
using namespace std;
int n,edges;
int hd[N],to[N<<1],nex[N<<1],val[N<<1];
void add(int u,int v,int c)
{
nex[++edges]=hd[u],hd[u]=edges,to[edges]=v,val[edges]=c;
}
namespace tree
{
int size[N],son[N],dep[N],dis[N],fa[N],top[N];
void dfs1(int u,int ff)
{
size[u]=1,fa[u]=ff;
for(int i=hd[u];i;i=nex[i])
if(to[i]!=ff)
{
dis[to[i]]=dis[u]+val[i],dep[to[i]]=dep[u]+1;
dfs1(to[i],u),size[u]+=size[to[i]];
if(size[to[i]]>size[son[u]]) son[u]=to[i];
}
}
void dfs2(int u,int tp)
{
top[u]=tp;
if(son[u]) dfs2(son[u],tp);
for(int i=hd[u];i;i=nex[i])
if(to[i]!=fa[u]&&to[i]!=son[u])
dfs2(to[i],to[i]);
}
int LCA(int x,int y)
{
while(top[x]!=top[y])
dep[top[x]]>dep[top[y]]?x=fa[top[x]]:y=fa[top[y]];
return dep[x]<dep[y]?x:y;
}
int Dis(int x,int y)
{
return dis[x]+dis[y]-(dis[LCA(x,y)]<<1);
}
};
namespace seg
{
int tot;
#define lson t[x].ls
#define rson t[x].rs
struct Node
{
int ls,rs,min;
}t[N*100];
int newnode()
{
t[++tot].min=inf;
return tot;
}
void pushup(int x)
{
t[x].min=inf;
if(lson) t[x].min=min(t[x].min,t[lson].min);
if(rson) t[x].min=min(t[x].min,t[rson].min);
}
void update(int &x,int l,int r,int p,int v)
{
if(!x) x=newnode();
if(l==r)
{
t[x].min=min(t[x].min,v);
return;
}
int mid=(l+r)>>1;
if(p<=mid) update(lson,l,mid,p,v);
else update(rson,mid+1,r,p,v);
pushup(x);
}
int query(int x,int l,int r,int L,int R)
{
if(!x) return inf;
if(l>=L&&r<=R) return t[x].min;
int mid=(l+r)>>1,re=inf;
if(L<=mid) re=min(re,query(lson,l,mid,L,R));
if(R>mid) re=min(re,query(rson,mid+1,r,L,R));
return re;
}
#undef lson
#undef rson
};
int root,sn;
int size[N],Fa[N],mx[N],vis[N],rt[N];
void getroot(int u,int ff)
{
size[u]=1,mx[u]=0;
for(int i=hd[u];i;i=nex[i])
if(to[i]!=ff&&!vis[to[i]])
getroot(to[i],u),size[u]+=size[to[i]],mx[u]=max(mx[u],size[to[i]]);
mx[u]=max(mx[u],sn-mx[u]);
if(mx[u]<mx[root]) root=u;
}
void dfs(int u,int ff)
{
size[u]=1;
for(int i=hd[u];i;i=nex[i])
if(to[i]!=ff&&!vis[to[i]])
dfs(to[i],u),size[u]+=size[to[i]];
}
void calc(int u,int ff,int dep,int tp)
{
seg::update(rt[tp],1,n,u,dep);
for(int i=hd[u];i;i=nex[i])
if(to[i]!=ff&&!vis[to[i]])
calc(to[i],u,dep+val[i],tp);
}
void prepare(int u)
{
vis[u]=1,calc(u,0,0,u);
for(int i=hd[u];i;i=nex[i])
if(!vis[to[i]])
dfs(to[i],u),root=0,sn=size[to[i]],getroot(to[i],u),Fa[root]=u,prepare(root);
}
int query(int u,int l,int r)
{
int re=seg::query(rt[u],1,n,l,r),U=u;
for(;Fa[u];u=Fa[u])
re=min(re, seg::query(rt[Fa[u]],1,n,l,r)+tree::Dis(U,Fa[u]));
return re;
}
int main()
{
int i,j,m;
// setIO("input");
scanf("%d",&n);
for(i=1;i<n;++i)
{
int a,b,c;
scanf("%d%d%d",&a,&b,&c),add(a,b,c),add(b,a,c);
}
tree::dfs1(1,0),tree::dfs2(1,1);
root=0,mx[root]=sn=n,getroot(1,0),prepare(root);
scanf("%d",&m);
for(i=1;i<=m;++i)
{
int l,r,x;
scanf("%d%d%d",&l,&r,&x);
printf("%d
",query(x,l,r));
}
return 0;
}