Cod sursa(job #1173996)

Utilizator Kira96Denis Mita Kira96 Data 21 aprilie 2014 16:19:50
Problema Lowest Common Ancestor Scor 20
Compilator cpp Status done
Runda Arhiva educationala Marime 1.49 kb
#include<fstream>
#define pb push_back
#include<vector>
#define N 100100
#define FOR(a,b,c) for(int a=b;a<=c;a++)
using namespace std;
ifstream f("lca.in");
ofstream g("lca.out");
vector<int> v[N],P[N];
int niv[N],T[N],arb[N],nrl,lant[N],n,m,x,y;
void dfs(int x,int p,int lvl)
{
    T[x]=p;
    niv[x]=lvl;
    arb[x]=1;
    int siz=v[x].size();
    siz--;
    FOR(i,0,siz)
    {
        if(v[x][i]!=p)
        {
            dfs(v[x][i],x,lvl+1);
            arb[x]+=arb[v[x][i]];
        }
    }
    if(arb[x]==1)
    {
        ++nrl;
        lant[x]=nrl;
        P[nrl].pb(x);
        return;
    }
    int hv=0;
    FOR(i,0,siz)
    {
        if(v[x][i]!=p)
        if(arb[v[x][i]]>arb[hv])
        hv=v[x][i];
    }
    lant[x]=lant[hv];
    P[lant[x]].pb(x);
}
int find(int x,int y)
{
    while(1)
    {
        if(lant[x]==lant[y])
        {
            if(niv[x]<niv[y])
            return x;
            else
            return y;
        }
        if(niv[x]<niv[y])
        swap(x,y);
        if(P[lant[x]].size()>P[lant[y]].size())
        swap(x,y);
        x=T[P[lant[x]][0]];
    }
}
int main ()
{
    f>>n>>m;
    FOR(i,2,n)
    {
        f>>x;
        v[i].pb(x);
        v[x].pb(i);
    }
    dfs(1,0,1);
    FOR(i,1,nrl)
    {
        int siz=P[i].size();
        siz--;
        FOR(j,0,siz/2)
        swap(P[i][j],P[i][siz-j]);
    }
    FOR(i,1,m)
    {
        f>>x>>y;
        g<<find(x,y)<<"\n";
    }
    return 0;
}