#include <iostream>
#include <fstream>
#include <bits/stdc++.h>
using namespace std;
ifstream f("arbint.in");
ofstream g("arbint.out");
const int Nmax = 100010;
int N, M, op, a, b, A[Nmax], aint[Nmax*2+10];
void build_aint(int node, int lft, int rgt){
if(lft == rgt){
aint[node] = A[lft];
return ;
}
int mid = (lft + rgt) / 2;
build_aint(node*2 , lft , mid);
build_aint(node*2+1, mid+1, rgt);
aint[node] = max(aint[node*2], aint[node*2+1]);
return ;
}
int get_max_aint(int node, int curr_left, int curr_right, int lft, int rgt){
if(curr_right < lft)
return 0;
if(curr_left > rgt)
return 0;
if(lft <= curr_left && curr_right <= rgt)
return aint[node];
int curr_mid = (curr_left + curr_right) / 2;
int curr_max = 0;
if(lft <= curr_mid)
curr_max = max(curr_max, get_max_aint(node*2, curr_left, curr_mid, lft, rgt));
if(curr_mid + 1 <= rgt)
curr_max = max(curr_max, get_max_aint(node*2+1, curr_mid+1, curr_right, lft, rgt));
return curr_max;
}
int get_max(int lft, int rgt){
return get_max_aint(1, 1, N, lft, rgt);
}
void update_aint(int node, int lft, int rgt, int pos){
if(lft == rgt){
aint[node] = A[lft];
return ;
}
int mid = (lft + rgt)/2;
if(pos <= mid)
update_aint(node*2, lft, mid, pos);
else
update_aint(node*2+1, mid+1, rgt, pos);
aint[node] = max(aint[node*2], aint[node*2+1]);
return ;
}
void update(int pos){
update_aint(1, 1, N, pos);
}
int main()
{
f>>N>>M;
for(int i=1;i<=N;i++)
f>>A[i];
build_aint(1, 1, N);
for(;M;M--){
f>>op>>a>>b;
if(op == 0){
g<<get_max(a, b)<<'\n';
}else{
A[a] = b;
update(a);
}
}
return 0;
}