Cod sursa(job #2105632)

Utilizator mariusmagureanmagurean marius mariusmagurean Data 13 ianuarie 2018 19:22:43
Problema Lowest Common Ancestor Scor 90
Compilator cpp Status done
Runda Arhiva educationala Marime 1.51 kb
/*
Solutie 30-40p
lowest common ancestor cu metoda bruta
Se parcurge arborele in adancime incepand de la 1 si pentru fiecare nod parcurs se retine nivelul pe care se gaseste.
Nivelul se va retine in vectorul nivel, radacina avand nivelul 0.
O interogare se rezolva pornind de la cele doua noduri si inaintand spre radacina cu nodul de nivel cel mai mare pana cand
se ajunge in acelasi nod.
Complexitatea dfs este O(n), fiecare query are O(n), deci complexitatea finala este O(n*m), unde n nr de noduri, m - nr interogari.
Retinem graful in matricea listelor de adiacenta arb, dar si in vectorul de tati t pentru a putea realiza mai rapid interogarea
Memoria folosita este de ordinul O(n), deci putina.
*/
#include<fstream>
#include<vector>

#define dim 100005

using namespace std;

int t[dim],nivel[dim];
int n,m;
ifstream fin("lca.in");
ofstream fout("lca.out");

vector<int>arb[dim];

void citire()
{
    fin>>n>>m;
    int i,j;
    for(i=2;i<=n;i++)
    {
        fin>>j;
        t[i]=j;
        arb[j].push_back(i);
    }
}

void dfs(int nod, int niv)
{
    nivel[nod]=niv;
    for(vector<int>::iterator it=arb[nod].begin();it!=arb[nod].end();it++)
        dfs(*it,niv+1);
}

int lca(int x, int y)
{
    while(x!=y)
        if(nivel[x]>nivel[y])
            x=t[x];
        else
            y=t[y];
    return x;
}

int main()
{
    int x,y;
    citire();
    dfs(1,0);
    for(int i=1;i<=m;i++)
    {
        fin>>x>>y;
        fout<<lca(x,y)<<"\n";
    }
    return 0;
}