Cod sursa(job #2329941)

Utilizator Username01Name Surname Username01 Data 27 ianuarie 2019 18:04:48
Problema Paduri de multimi disjuncte Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 1.54 kb
#include <stdio.h>

using namespace std;
FILE *f,*g;
int n,m,tata[100002],rang[100002];
/*Compresia drumurilor: Atunci cand facem o interogare, dupa ce am aflat in ce multime se afla nodul x,
 mai parcurgem o data drumul de la x la radacina si unim toate nodurile direct de radacina. Astfel data
  viitoare cand vom avea o interogare pentru unul din aceste noduri vom ajunge intr-un singur pas la radacina*/

int multime(int x)
{
    int rad=x,aux;
    while(rad!=tata[rad])///cat timp nu am ajuns la radacina arborelui
        rad=tata[rad];///determinam in ce multime se afla nodul x
    ///rad- reprezinta radacina nodului x
    return rad;
}

void reunesc(int x, int y)
{
    x=multime(x);
    y=multime(y);
    if(x==y) return ;
    if(rang[x]<rang[y])
        tata[x]=y;
    else
        tata[y]=x;
    if(rang[x]==rang[y])
        ++rang[x];
}

void read()
{
    int i,caz,x,y;
    fscanf(f,"%d %d",&n,&m);
    for(i=1;i<=n;++i)
        tata[i]=i;
    for(i=1;i<=m;++i)
    {
        fscanf(f,"%d %d %d",&caz,&x,&y);
        if(caz==1)///reunirea multimilor in care se afla x si a celor in care se afla y
            reunesc(multime(x),multime(y));
        else
        {
            if(multime(x)==multime(y))///sea afla x si y in aceiasi multime
                fprintf(g,"DA\n");
            else
                fprintf(g,"NU\n");
        }
    }
}
int main()
{
    int i,caz;
    f=fopen("disjoint.in","r");
    g=fopen("disjoint.out","w");
    read();
    fclose(f);
    fclose(g);
    return 0;
}