#include <bits/stdc++.h>
#define REP(i,n) for (long long i=0;i<(n);i++)
#define FOR(i,a,b) for (long long i=(a);i<(b);i++)
#define RREP(i,n) for(long long i=n;i>=0;i--)
#define RFOR(i,a,b) for(long long i=(a);i>(b);i--)
#define dump1d_arr(array) REP(i,array.size()) cerr << #array << "[" << (i) << "] ==> " << (array[i]) << endl;
#define dump2d_arr(array) REP(i,array.size()) REP(j,array[i].size()) cerr << #array << "[" << (i) << "]" << "[" << (j) << "] ==> " << (array[i][j]) << endl;
#define dump(x)  cerr << #x << " => " << (x) << endl;
#define dumpP(p) cerr << "( " << p.first << " , " << p.second << " )" << ends;
#define CLR(vec) { REP(i,vec.size()) vec[i] = 0; } 
#define SORT(c) sort((c).begin(),(c).end())
#define MIN(vec) *min_element(vec.begin(), vec.end());
#define MAX(vec) *max_element(vec.begin(), vec.end());
#define UNIQ(vec) vec.erase(unique(vec.begin(), vec.end()),vec.end());
#define IN(n,m)  (!(m.find(n) == m.end()))
#define ENUM(m) for (auto itr = m.begin(); itr != m.end(); ++itr)
#define dump_MAP(m) for(auto itr = m.begin(); itr != m.end(); ++itr) { cerr << itr->first << " --> "  << itr->second << endl; }
#define FINDL(vec,x) (lower_bound(vec.begin(),vec.end(),x) - vec.begin())
#define FINDU(vec,x) (upper_bound(vec.begin(),vec.end(),x) - vec.begin())
#define ROUND(N) setprecision(N)
#define ROUND_PRINT(N,val) cout << fixed;cout << setprecision(N) << val << endl
using namespace std;
/*
struct Monoid {
    using T = _underlying_set_;
    static  T op(const T& a, const T& b) { return _a_op_b_; }
    static constexpr T identity() { return _identity_element_; }
};
*/

// 1-index
template <class Monoid>
class SegTree {
   private:
    using T = typename Monoid::T;
    size_t n;
    const size_t sz;
    typedef tuple<int,size_t,size_t> tp;
    vector<T> t;

    void prop_to(size_t i) { t[i] = Monoid::op(t[2*i+1],t[2*i+2]); }

   public:
    SegTree(size_t m, const T& v = Monoid::identity())
        : sz(m), t(2*m-1, v) {}

    template <class InputIt>
    SegTree(InputIt first, InputIt last)
        : sz(distance(first, last)){
        n = 1; while(n < sz) n <<= 1;
        t.resize(2*n-1,Monoid::identity());
        copy(first, last, begin(t) + (n-1));
        for (int i = (n-2); i >= 0; --i) prop_to(i);
    }

    void set(size_t i, const T& v) {
        t[i += (n-1)] = v;
        while (i && ((--i) >>= 1)) prop_to(i);
        if(n >= 2) prop_to(0);
    }

    //T get(size_t i) { return t[i + (n-1)]; }

    T getminval(size_t l, size_t r) {
        T ret = Monoid::identity();
        stack<tp> st;
        st.push(make_tuple(0,0,n));
        while (!st.empty()) {
            tp state = st.top();st.pop();
            size_t lb = get<1>(state);
            size_t ub = get<2>(state);
            int node = get<0>(state);
            if (r <= lb || ub <= l) continue;
            if (l <= lb && ub <= r) ret = Monoid::op(ret,t[node]);
            else {
                st.push(make_tuple(2*node+1,lb,(lb+ub)/2));
                st.push(make_tuple(2*node+2,(lb+ub)/2,ub));
            }
        }
        return ret;
    }
};

struct RMQ {
    using T = int;
    static T op(const T& a, const T& b) { return min(a, b); }
    static constexpr T identity() {return numeric_limits<T>::max(); }
};

typedef long long LL;
int main(void) {
    int n,q,com,x,y;
    cin >> n >> q;
    vector<int> a(n,numeric_limits<int>::max());
    SegTree<RMQ> sg(a.begin(),a.end());
    REP(i,q) {
        cin >> com >> x >> y;
        if (com) cout << sg.getminval(x,y+1) << endl;
        else sg.set(x,y);
    }
}


Measured memory_bytes: 4160