#include <stdio.h>
#define MAXN 100000
#define MAX(a, b) ((a)>(b)?(a):(b))
struct SegmentTree{
private:
int aint[4*MAXN];
int n;
void update(int node, int s, int d, int pos, int val){
if(s==d && s==pos){
aint[node] = val;
//printf("%d {%d %d}: %d\n", node, s, d, aint[node]);
}
else{
int m = (s+d)/2;
if(pos<=m)
update(node*2, s, m, pos, val);
else
update(node*2+1, m+1, d, pos, val);
aint[node] = MAX(aint[node*2], aint[node*2+1]);
//printf("%d {%d %d}: %d\n", node, s, d, aint[node]);
}
}
int query(int node, int s, int d, int a, int b){
if(a<=s && d<=b){
return aint[node];
}
else{
int max = 0;
int st = 0;
int dr = 0;
int m = (s+d)/2;
if(a<=m)
st = query(node*2, s, m, a, b);
if(b>m)
dr = query(node*2+1, m+1, d, a, b);
max = MAX(st, dr);
//printf("%d %d: %d\n", s, d, max);
return max;
}
}
public:
void update(int pos, int val){
update(1, 0, n-1, pos, val);
}
int query(int a, int b){
return query(1, 0, n-1, a, b);
}
void init(int n){
this->n = n;
}
};
int n, m;
SegmentTree aint;
int main(){
FILE *fin, *fout;
fin = fopen("arbint.in", "r");
fout = fopen("arbint.out", "w");
fscanf(fin, "%d%d", &n, &m);
aint.init(n);
for(int i=0; i<n; i++){
int val;
fscanf(fin, "%d", &val);
aint.update(i, val);
}
//printf("%d\n", aint.query(0, 0));
//return 0;
for(int i=0; i<m; i++){
int type, a, b;
fscanf(fin, "%d %d %d", &type, &a, &b);
if(type==0)
fprintf(fout, "%d\n", aint.query(a-1, b-1));
else
aint.update(a-1, b);
}
fclose(fout);
fclose(fin);
return 0;
}