Cod sursa(job #1507949)

Utilizator tamionvTamio Vesa Nakajima tamionv Data 22 octombrie 2015 08:11:23
Problema Radiatie Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 2.11 kb
#include <fstream>
#include <vector>
#include <numeric>
#include <algorithm>
#include <tuple>
#include <iostream>
using namespace std;

class merge_find{
	int n;
	vector<int> tata, adancime, val_to_tata;
public:
	merge_find(const int N): n(N), tata(n, 0), adancime(n, 1), val_to_tata(n, 0){
		iota(begin(tata), end(tata), 0); }
	int find(int x){
		for( ; x != tata[x]; x = tata[x]);
		return x; }
	void merge(int a, int b, const int l){
		a = find(a), b = find(b);
		if(a == b){
			return; }
		if(adancime[a] < adancime[b]){
			swap(a, b); }
		else if(adancime[a] == adancime[b]){
			++adancime[a]; }
		tata[b] = a;
		val_to_tata[b] = l; }
	void export_tree(vector<int>& t, vector<vector<int> >& c, vector<int>& val){
		t = tata;
		for(int i = 0; i < n; ++i){
			if(i != t[i]){
				c[t[i]].push_back(i); } }
		val = val_to_tata; } };

void make_adancimi(const int cur, const vector<vector<int> >& copii, vector<int>& adanc){
	for(const auto next : copii[cur]){
		adanc[next] = adanc[cur]+1;
		make_adancimi(next, copii, adanc); } }

int query(int a, int b, const vector<int>& tata, const vector<int>& adanc, const vector<int>& val){
	int rez = 0;
	for( ; adanc[a] < adanc[b]; rez = max(rez, val[b]), b = tata[b]);
	for( ; adanc[a] > adanc[b]; rez = max(rez, val[a]), a = tata[a]);
	for( ; a != b; rez = max({rez, val[a], val[b]}), a = tata[a], b = tata[b]);
	return rez; }

int find_rad(const vector<int>& tata){
	for(int i = 0; ; ++i){
		if(tata[i] == i){
			return i; } } }

int main(){
	ifstream f("radiatie.in");
	ofstream g("radiatie.out");
	int n, m, k;
	f >> n >> m >> k;
	vector<tuple<int, int, int> > muc(m);
	for(auto& x : muc){
		f >> get<2>(x) >> get<1>(x) >> get<0>(x); }
	sort(begin(muc), end(muc));

	merge_find mf(n+1);

	for(const auto x : muc){
		mf.merge(get<1>(x), get<2>(x), get<0>(x)); }
	for(int i = 1; i <= n; ++i){
		mf.merge(0, i, 1000000001); }
	vector<int> tata(n+1), val(n+1);
	vector<vector<int> > copii(n+1);

	mf.export_tree(tata, copii, val);

	vector<int> adanc(n+1, 0);
	make_adancimi(find_rad(tata), copii, adanc);
	for(int i = 0, a, b; i < k; ++i){
		f >> a >> b;
		g << query(a, b, tata, adanc, val) << '\n'; }
	return 0; }