大二训练第二周 F - How far away ? lca

F - How far away ?
Time Limit:1000MS     Memory Limit:32768KB     64bit IO Format:%I64d & %I64u

Description

There are n houses in the village and some bidirectional roads connecting them. Every day peole always like to ask like this "How far is it if I want to go from house A to house B"? Usually it hard to answer. But luckily int this village the answer is always unique, since the roads are built in the way that there is a unique simple path("simple" means you can't visit a place twice) between every two houses. Yout task is to answer all these curious people.
 

Input

First line is a single integer T(T<=10), indicating the number of test cases. 
  For each test case,in the first line there are two numbers n(2<=n<=40000) and m (1<=m<=200),the number of houses and the number of queries. The following n-1 lines each consisting three numbers i,j,k, separated bu a single space, meaning that there is a road connecting house i and house j,with length k(0<k<=40000).The houses are labeled from 1 to n. 
  Next m lines each has distinct integers i and j, you areato answer the distance between house i and house j.
 

Output

For each test case,output m lines. Each line represents the answer of the query. Output a bland line after each test case.
 

Sample Input

       
       
2 3 2 1 2 10 3 1 15 1 2 2 3 2 2 1 2 100 1 2 2 1
 

Sample Output

       
       
10 25 100 100
 
模板题啦。。
ACcode:
 
#pragma warning(disable:4786)//使命名长度不受限制
#pragma comment(linker, "/STACK:102400000,102400000")//手工开栈
#include <map>
#include <set>
#include <queue>
#include <cmath>
#include <stack>
#include <cctype>
#include <cstdio>
#include <cstring>
#include <stdlib.h>
#include <iostream>
#include <algorithm>
#define rd(x) scanf("%d",&x)
#define rd2(x,y) scanf("%d%d",&x,&y)
#define rds(x) scanf("%s",x)
#define rdc(x) scanf("%c",&x)
#define ll long long int
#define maxn 100005
#define mod 1000000007
#define INF 0x3f3f3f3f //int 最大值
#define FOR(i,f_start,f_end) for(int i=f_start;i<=f_end;++i)
#define MT(x,i) memset(x,i,sizeof(x))
#define PI  acos(-1.0)
#define E  exp(1)
using namespace std;
struct node{
    int id,val,next;
}e[maxn<<1];
int fa[maxn],dis[maxn],pre[maxn],x[maxn],y[maxn],z[maxn];
bool vis[maxn];
int n,m,cnt,loop;
void add(int u,int v,int w){
    e[cnt].id=u;
    e[cnt].val=w;
    e[cnt].next=pre[v];
    pre[v]=cnt++;
    e[cnt].id=v;
    e[cnt].val=w;
    e[cnt].next=pre[u];
    pre[u]=cnt++;
}
int find(int x){return x==fa[x]?x:fa[x]=find(fa[x]);}
void tarjan(int k){
    vis[k]=true;
    fa[k]=k;
    FOR(i,1,m){
        if(x[i]==k&&vis[y[i]])
            z[i]=find(y[i]);
        if(y[i]==k&&vis[x[i]])
            z[i]=find(x[i]);
    }
    for(int i=pre[k];i!=-1;i=e[i].next){
        if(!vis[e[i].id]){
            dis[e[i].id]=dis[k]+e[i].val;
            tarjan(e[i].id);
            fa[e[i].id]=k;
        }
    }
}
void init(){
    FOR(i,0,maxn){
        pre[i]=-1;
        vis[i]=x[i]=y[i]=z[i]=0;
    }
}
int main(){
    rd(loop);
    while(loop--){
        int u,v,w;
        rd2(n,m);cnt=0;
        init();
        FOR(i,1,n-1){
            rd2(u,v);rd(w);
            add(u,v,w);
        }
        FOR(i,1,m)rd2(x[i],y[i]);
        dis[1]=0;tarjan(1);
        FOR(i,1,m)
            printf("%d\n",dis[x[i]]+dis[y[i]]-2*dis[z[i]]);
    }
    return 0;
}
/*
2
3 2
1 2 10
3 1 15
1 2
2 3

2 2
1 2 100
1 2
2 1
*/

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值