Cod sursa(job #1060967)

Utilizator Al3ks1002Alex Cociorva Al3ks1002 Data 18 decembrie 2013 22:46:51
Problema Radiatie Scor 30
Compilator cpp Status done
Runda Arhiva de probleme Marime 2.32 kb
#include<cstdio>
#include<algorithm>
#include<vector>

#define PII pair<int,int>
#define pb push_back
#define mp make_pair

using namespace std;

const int MMAX = 30005;
const int NMAX = 15005;
const int LMAX = 15;

int N,M,K,i,j,X,Y,C,A,B,E,F;
int D[NMAX],Level[NMAX];
int S[NMAX][LMAX],Max[NMAX][LMAX];

vector<PII> G[NMAX];

struct Edge
{
    int X,Y,C;
};
Edge V[MMAX];

bool cmp(Edge A,Edge B)
{
    return A.C<B.C;
}

int Find(int X)
{
    if(D[X]!=X) D[X]=Find(D[X]);
    return D[X];
}

void Unite(int X,int Y)
{
    D[X]=Y;
}

void DFS(int X,int Y)
{
    Level[X]=Y;
    for(vector<PII>::iterator it=G[X].begin();it!=G[X].end();it++)
        if(!Level[it->first])
        {
            DFS(it->first,Y+1);
            S[it->first][0]=X;
            Max[it->first][0]=it->second;
        }
}

void Read()
{
    freopen("radiatie.in","r",stdin);
    freopen("radiatie.out","w",stdout);
    scanf("%d%d%d",&N,&M,&K);
    for(i=1;i<=M;i++) scanf("%d%d%d",&V[i].X,&V[i].Y,&V[i].C);
}

void BuildAPM()
{
    sort(V+1,V+M+1,cmp);
    for(i=1;i<=N;i++) D[i]=i;
    for(i=1;i<=M;i++)
    {
        X=V[i].X; Y=V[i].Y; C=V[i].C;
        A=Find(X); B=Find(Y);
        if(A!=B)
        {
            Unite(A,B);
            G[X].pb(mp(Y,C));
            G[Y].pb(mp(X,C));
        }
    }
}

void BuildAncestors()
{
    DFS(1,1);
    for(i=1;(1<<i)<=N;i++)
        for(j=1;j<=N;j++)
        {
            S[j][i]=S[S[j][i-1]][i-1];
            Max[j][i]=max(Max[j][i-1],Max[S[j][i-1]][i-1]);
        }
}

void AnswerQueries()
{
    for(;K;K--)
    {
        scanf("%d%d",&X,&Y);
        if(Level[X]>Level[Y]) swap(X,Y);
        C=Level[Y]-Level[X]; E=F=0;
        for(i=0,j=1;j<=C;i++,j<<=1)
            if(j&C)
            {
                F=max(F,Max[Y][i]);
                Y=S[Y][i];
            }
        if(X!=Y)
        {
            for(A=0;(1<<A)<=Level[X];A++);
            for(i=A;i;i--)
                if(S[X][i] && S[X][i]!=S[Y][i])
                {
                    E=max(E,Max[X][i]);
                    F=max(F,Max[Y][i]);
                    X=S[X][i]; Y=S[Y][i];
                }
        }
        printf("%d\n",max(E,F));
    }
}

int main()
{
    Read();
    BuildAPM();
    BuildAncestors();
    AnswerQueries();
    return 0;
}