#include <iostream>
#include <fstream>
using namespace std;
ifstream in("arbint.in");
ofstream out("arbint.out");
const int MAX=100000;
int m, n;
int segtree[MAX+5], v[MAX+1];
void build(int node, int left, int right)
{
if(left==right)
{
segtree[node] = v[left];
}
else
{
int mij=(left+right)/2;
build(node*2, left, mij);
build(node*2+1, mij+1, right);
segtree[node]=max(segtree[2*node], segtree[2*node+1]);
}
}
void update(int lf, int rg, int node, int pos_upd, int val_upd)
{
if(lf==rg) //left==right
{
segtree[node]=val_upd;
return;
}
int med=(lf+rg)/2;
if(pos_upd<=med)
{
update(lf, med, 2*node, pos_upd, val_upd);
}
else
{
update(med+1, rg, 2*node+1, pos_upd, val_upd);
}
segtree[node]=max(segtree[2*node], segtree[2*node+1]); //cei 2 fii
}
int query(int lf, int rg, int node, int q_lf, int q_rg)
{
if (lf >=q_lf && rg<=q_rg)
{
return segtree[node];
}
int med=(lf+rg)/2;
int lfans=-MAX;
int rgans=-MAX;
if(med >= q_lf)
lfans = query(lf, med, 2*node, q_lf, q_rg);
if(med + 1 <= q_rg)
{
rgans = query(med+1, rg, 2*node+1, q_lf, q_rg);
}
return max(lfans, rgans);
}
int main()
{
in>>n>>m;
int maxLen=1;
while(maxLen<n)
maxLen=maxLen*2;
//cout<<maxLen;
for(int i=1; i<=n; ++i)
{
in >> v[i];
}
build(1, 1, maxLen);
for(int i=0; i<m; ++i)
{
int op;
in>>op;
if(op==0)
{
int lf, rg;
in >> lf >> rg;
out<<query(1, maxLen, 1, lf, rg)<<'\n';
}
else
{
int poz, val;
in >> poz >> val;
update(1, maxLen, 1, poz, val);
}
}
return 0;
}