Cod sursa(job #1568241)

Utilizator CostanMiriamCostan Miriam CostanMiriam Data 13 ianuarie 2016 23:44:36
Problema Arbore Scor 95
Compilator cpp Status done
Runda Arhiva de probleme Marime 2.23 kb
#include <fstream>
#include <vector>
#include <cmath>
#include <bitset>
#include <algorithm>

#define DIM 100010

using namespace std;

ifstream fin("arbore.in");
ofstream fout("arbore.out");

int n, m, root;

vector<int> L[DIM];

int position;

int parc[DIM], start[DIM], finish[DIM];

bool vis[DIM];

int v[DIM], add[350];

bitset<1000010> ok[350];

void DFS(int node) {

	vis[node] = true;

	parc[++position] = node;

	start[node] = position;

	for (int i = 0; i < L[node].size(); i++) {

		int child = L[node][i];

		if (!vis[child])
			DFS(child);

	}

	finish[node] = position;

}

void update(int node, int sum) {

	int Start = start[node];
	int Finish = finish[node];

	int SR = (Start - 1) / root + 1;
	int SF = (Finish - 1) / root + 1;

	for (int i = SR; i <= SF; i++) {
	
		if ((i - 1) * root + 1 >= Start && i * root <= Finish) {

			add[i] += sum;

			continue;

		}

		if (i * root >= Start || (i - 1) * root + 1 <= Finish) {

			int first = (i - 1) * root + 1;
			int last = i * root;
			
			first = max(first, Start);
			last = min(last, Finish);
			
			for (int j = (i - 1) * root + 1; j <= i * root && j < n; j++)
				ok[i][v[j]] = 0;

			for (int j = (i - 1) * root + 1; j <= i * root && j < n; j++) {
				
				v[j] += add[i];
				
				if (j >= first && j <= last)
					v[j] += sum;
				
				ok[i][v[j]] = 1;
			
			}
			
			add[i] = 0;

		}


	}

}

int query(int sum) {

	for (int i = 1; i <= (n - 1) / root + 1; i++) {
		
		if (sum - add[i] < 0)
			continue;

		if (ok[i][sum - add[i]]) 
			for (int j = (i - 1) * root + 1; j <= i * root; j++) 
				if (v[j] + add[i] == sum) 
					return parc[j];
			
	}

	return -1;

}

int main() {

	fin >> n >> m;

	root = sqrt(n * 1.0);

	for (int i = 1; i <= (n - 1) / root + 1; i++)
		ok[i][0] = 1;

	for (int i = 1; i < n; i++) {

		int x, y;

		fin >> x >> y;

		L[x].push_back(y);
		L[y].push_back(x);

	}

	DFS(1);

	while (m--) {

		int op;

		fin >> op;

		if (op == 1) {

			int node, sum;

			fin >> node >> sum;

			update(node, sum);

			continue;

		}

		int sum;

		fin >> sum;

		fout << query(sum) << "\n";

	}

	return 0;

}

//Miriam e tare!