#include<cstdio>
#include<iostream>
using namespace std;
#define MAX 300001
int N , M , v[MAX] , A[2*MAX] , maxx;
void build(int n, int l , int r);
void query(int n, int l , int r , int a, int b);
void update(int n , int l , int r ,int poz , int val);
int main()
{
int a , b , t;
freopen("arbint.in" , "r" , stdin );
freopen("arbint.out" , "w" , stdout );
scanf("%d%d" , &N , &M );
for(int i = 1 ; i <= N ; ++i )
scanf("%d" , &v[i]);
build(1,1,N);
for(int i = 1 ; i <= M ; ++i )
{
maxx = -1;
scanf("%d%d%d" , &t , &a , &b);
if(t == 0)
{
query(1,1,N,a,b);
printf("%d\n" , maxx );
}
else update(1,1,N,a,b);
}
return 0;
}
void build(int n , int l , int r)
{
if(l == r)A[n] = v[l];
else
{
int m = (l+r)/2;
build(2*n,l,m);
build(2*n+1,m+1,r);
A[n] = max(A[2*n],A[2*n+1]);
}
}
void query(int n , int l , int r , int a , int b)
{
if(a <= l && b >= r)maxx = max(maxx,A[n]);
else
{
int m = (l+r)/2;
if(a <= m)
query(2*n,l,m,a,b);
if(b > m)
query(2*n+1,m+1,r,a,b);
}
}
void update(int n , int l , int r , int a , int b)
{
if(l == r)A[n] = b;
else
{
int m = (l+r)/2;
if(a <= m)
update(2*n,l,m,a,b);
else
update(2*n+1,m+1,r,a,b);
A[n] = max(A[2*n],A[2*n+1]);
}
}