Cod sursa(job #476357)

Utilizator vlad.maneaVlad Manea vlad.manea Data 10 august 2010 19:57:08
Problema Paduri de multimi disjuncte Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 2.07 kb
/* ------ */

#ifndef _ALGORITHM_H
#define _ALGORITHM_H
#include <fstream>
using namespace std;

/**
	Algorithm abstract class
	specifies protocol
*/
class Algorithm
{
protected:

	istream &in;
	ostream &out;

	/**
		algorithm method
		instantiates i/o
	*/
	Algorithm(istream &, ostream &);
};

#endif

#ifndef _UNIONFIND_H
#define _UNIONFIND_H

#include <vector>
using namespace std;

/**
	UnionFind class
	solves the disjoint sets union find problem
*/
class UnionFind: public Algorithm
{
	int N;
	vector<int> Ftr;

public:

	/**
		unionfind method
		runs algorithm
	*/
	UnionFind(istream &, ostream &);

private:

	/**
		union method
		reunites two sets
	*/
	void Union(int, int);

	/**
		find method
		finds set
	*/
	int Find(int);

	/**
		update method
		updates set
	*/
	void Update(int, int);
};

#endif

/**
	algorithm method
	instantiates i/o
*/
Algorithm::Algorithm(istream &inp, ostream &outp): in(inp), out(outp)
{

}

/**
	unionfind method
	runs algorithm
*/
UnionFind::UnionFind(istream &in, ostream &out): Algorithm(in, out), N(0)
{
	int x, y, c, m;

	in >> N;
	Ftr.assign(N + 1, -1);

	in >> m;
	while (m--)
	{
		in >> c >> x >> y;
		if (c == 1)
			Union(x, y);
		else
			if (Find(x) == Find(y))
				out << "DA\n";
			else
				out << "NU\n";
	}
}

/**
	union method
	reunites two sets
*/
void UnionFind::Union(int x, int y)
{
	int i, j, c;

	i = Find(x);
	j = Find(y);

	if (Ftr[i] > Ftr[j])
	{
		Ftr[i] = j;
		c = j;
	}
	else if (Ftr[i] < Ftr[j])
	{
		Ftr[j] = i;
		c = i;
	}
	else
	{
		Ftr[i] = j;
		--Ftr[j];
		c = j;
	}

	Update(x, c);
	Update(y, c);
}

/**
	find method
	finds set
*/
int UnionFind::Find(int x)
{
	int i;

	for (i = x; Ftr[i] > 0; i = Ftr[i]); 
	
	Update(x, i);
	return i;
}

/**
	update method
	updates set
*/
void UnionFind::Update(int x, int c)
{
	int i;

	for (i = x; Ftr[i] > 0; i = x)
	{
		x = Ftr[i];
		Ftr[i] = c;
	}
}

/* ------ */



int main()
{
	ifstream fin("disjoint.in");
	ofstream fout("disjoint.out");
	UnionFind mflow(fin, fout);

	fin.close();
	fout.close();
	return 0;
}