Cod sursa(job #1618995)

Utilizator tamionvTamio Vesa Nakajima tamionv Data 28 februarie 2016 10:48:36
Problema Arbore Scor 0
Compilator cpp Status done
Runda Arhiva de probleme Marime 2.33 kb
#include <fstream>
#include <vector>
#include <unordered_map>
#include <iostream>
using namespace std;

const int chunk_sz = 330;

int find_chunk(const int x){
	return x/chunk_sz; }

int first_of_chunk(const int x){
	return x*chunk_sz; }

int last_of_chunk(const int x){
	return first_of_chunk(x+1)-1; }

class chunk_structure{
	int n, n_chunks;
	vector<int> v, delta_chunks;
	vector<unordered_map<int, int>> chunks;
	void do_chunk(const int x){
		const int st = first_of_chunk(x), dr = min(last_of_chunk(x), n-1);
		chunks[x].clear();
		for(int i = st; i <= dr; ++i){
			v[i] += delta_chunks[x];
			chunks[x][v[i]] = i; }
		delta_chunks[x] = 0; }
public:
	chunk_structure(const int N): n(N), n_chunks(find_chunk(n-1)+1), v(n, 0),
			delta_chunks(n_chunks, 0), chunks(n_chunks){
		for(int i = 0; i < n_chunks; ++i){
			do_chunk(i); } }
	void update(const int st, const int dr, const int delta){
		const int ch_st = find_chunk(st), ch_dr = find_chunk(dr);
		if(ch_st == ch_dr){
			for(int i = st; i <= dr; ++i){
				v[i] += delta; }
			do_chunk(ch_st);
			return; }

		for(int i = ch_st+1; i < ch_dr; ++i){
			delta_chunks[i] += delta; }
		for(int i = st, stop = min(last_of_chunk(ch_st), n-1); i <= stop; ++i){
			v[i] += delta; }
		for(int i = first_of_chunk(ch_dr); i <= dr; ++i){
			v[i] += delta; }
		do_chunk(ch_st);
		do_chunk(ch_dr); }
	int query(const int x){
		for(int i = 0; i < n_chunks; ++i){
			auto it = chunks[i].find(x-delta_chunks[i]);
			if(it != chunks[i].end()){
				return it->second; } }
		return -2; } };

void dfs(const int cur, const int prev, const vector<vector<int>>& v,
	vector<int>& st, vector<int>& dr, vector<int>& euler){
	euler.push_back(cur);
	st[cur] = dr[cur] = euler.size()-1;
	for(int i = 0; i < v[cur].size(); ++i){
		if(v[cur][i] != prev){
			dfs(v[cur][i], cur, v, st, dr, euler);
			dr[cur] = dr[v[cur][i]]; } } }

int main(){
	ifstream f("arbore.in");
	ofstream g("arbore.out");
	int n, m;
	f >> n >> m;

	vector<vector<int>> v(n);
	for(int i = 0, a, b; i < n-1; ++i){
		f >> a >> b;
		--a, --b;
		v[a].push_back(b);
		v[b].push_back(a); }

	vector<int> st(n), dr(n), euler;
	dfs(0, -1, v, st, dr, euler);

	chunk_structure chst(n);

	for(int i = 0, t, p, s; i < m; ++i){
		f >> t;
		if(t == 1){
			f >> p >> s;
			--p;

			chst.update(st[p], dr[p], s); }
		else{
			f >> s;
			g << (euler[chst.query(s)]+1) << '\n'; } }
	g.flush();
	return 0; }