Problem:
Range Minimum Query (RMQ)

Write a program which manipulates a sequence A = {a0, a1, . . . , an-1} with the following operations:

find(s, t): report the minimum element in as, as+1, . . . ,at.

update(i, x): change ai to x.

Note that the initial values of ai (i = 0, 1, . . . , n−1) are 231-1.

Input

n q
com0 x0 y0
com1 x1 y1
...
comq−1 xq−1 yq−1

In the first line, n (the number of elements in A) and q (the number of queries) are given. Then, q queries are given where com represents the type of queries. '0' denotes update(xi, yi) and '1' denotes find(xi, yi).

Output

For each find operation, print the minimum element.

Constraints

1 ≤ n ≤ 100000

1 ≤ q ≤ 100000

If comi is 0, then 0 ≤ xi < n, 0 ≤ yi < 231-1.

If comi is 1, then 0 ≤ xi < n, 0 ≤ yi < n.

Sample Input 1

3 5
0 0 1
0 1 2
0 2 3
1 0 2
1 1 2

Sample Output 1

1
2

Sample Input 2

1 3
1 0 0
0 0 5
1 0 0

Sample Output 2

2147483647
5

Solution in C (judge verdict: Accepted)

#include <stdio.h>
#include <stdlib.h>
#include <limits.h>

int n, q, i; 
int* D;

void initValue(void);
int min(int a, int b);
void initRMQ( int n_);
void update(int k, int a);
int findMin(int a, int b);
int query(int a , int b, int k, int l, int r);


int main(int argc, char* argv[]){

    initValue();
	
	initRMQ(n);


	int a, b;
	int com, ans;
	
    while(q > 0){
		
        scanf("%d %d %d",&com, &a, &b);
		
        if(com){
			ans = findMin(a,b);
			printf("%d\n",ans);
		}else{
			update(a,b);
		}	
		q--;
	}

	return 0;
}

int min(int a, int b){
	if(a > b){
	return b;
	}else{
	return a;
	}
}

void initValue(void){

	scanf("%d %d", &n, &q);
	return;
}

void initRMQ(int n_){
	
	n = 1;
	while(n < n_){
		n *= 2;
	}
	
	D = malloc(sizeof(int)* (2 * n - 1));
	
    if(D == NULL){
		printf("Init Array Failed, no memory or size is wrong\n");
		return;
	}

	for(i = 0; i< 2*n-1 ; i++){
		D[i] = INT_MAX;
	}
	return;
}


void update(int k , int a){
	k += n - 1;
	D[k] = a;
	
    while (k > 0){
		k = (k-1)/2;
		D[k] = min(D[k*2+1], D[k*2+2]);
	}
}

int findMin(int a, int b){
	
	return query( a, b+1, 0, 0, n);
}

int query(int a, int b, int k , int l , int r){
	
	if(r <= a || b <= l){
		return INT_MAX;
	}
	if(a <= l && r <= b){
		return D[k];
	}
	
	int vl = query(a, b, k * 2 + 1, l , (l + r) / 2);
	
	int vr = query(a, b, k * 2 + 2, (l + r)/2, r);
	return min(vl, vr);
}