Cod sursa(job #1278072)

Utilizator Marius96Marius Gavrilescu Marius96 Data 28 noiembrie 2014 14:28:19
Problema Arbori de intervale Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 1.54 kb
#include<cstdio>
#include<algorithm>
using std::max;

struct node {
	int v;
	node *s, *d;
} *roots[100005];

int v[270000], rn;

void update(node *nd, int l, int r, int a, int b, int v){
	int m = (l + r) / 2;
	if(l == r) {
		nd->v = v;
		return;
	} else if(b <= m) {
		nd->s = new node(*nd->s);
		update(nd->s, l, m, a, b, v);
	} else if(m + 1 <= a) {
		nd->d = new node(*nd->d);
		update(nd->d, m+1, r, a, b, v);
	} else {
		nd->s = new node(*nd->s);
		nd->d = new node(*nd->d);
		update(nd->s, l, m, a, m, v);
		update(nd->d, m+1, r, m+1, b, v);
	}

	nd->v = max(nd->s->v, nd->d->v);
}

int query(node *nd, int l, int r, int a, int b){
	int m = (l + r) / 2;
	if(l == a && r == b)
		return nd->v;
	else if(b <= m)
		return query(nd->s, l, m, a, b);
	else if(m + 1 <= a)
		return query(nd->d, m+1, r, a, b);
	else
		return std::max(query(nd->s, l, m, a, m), query(nd->d, m+1, r, m+1, b));
}

void build(node *nd, int l, int r){
	int m = (l + r) / 2;
	if(l == r)
		nd->v = v[l];
	else {
		nd->s = new node;
		nd->d = new node;
		build(nd->s, l, m);
		build(nd->d, m+1, r);
		nd->v = std::max(nd->s->v, nd->d->v);
	}
}

int main(void){
	freopen("arbint.in", "r", stdin);
#ifdef INFOARENA
	freopen("arbint.out", "w", stdout);
#endif

	int n, m;
	scanf("%d%d", &n, &m);
	for(int i = 1 ; i <= n ; i++)
		scanf("%d", v + i);
	roots[0] = new node;
	build(roots[0], 0, n);

	while(m--){
		int op, a, b;
		scanf("%d%d%d", &op, &a, &b);
		if(op){
			roots[rn+1] = new node(*roots[rn]);
			update(roots[++rn], 0, n, a, a, b);
		} else
			printf("%d\n", query(roots[rn], 0, n, a, b));
	}
}