#include <bits/stdc++.h>
using namespace std;
template <typename T1, typename T2>
inline ostream &operator<<(ostream &os, const pair<T1, T2> &p) {
  return os << "(" << p.first << ", " << p.second << ")";
}
template <typename T, size_t N>
inline ostream &operator<<(ostream &os, const array<T, N> &a) {
  os << "[";
  int cnt = 0;
  for (auto &val : a) {
    if (cnt++) os << ", ";
    os << val;
  }
  os << "]";
  return os;
}
template <typename T>
inline ostream &operator<<(ostream &os, const vector<T> &v) {
  os << "[";
  int cnt = 0;
  for (auto &val : v) {
    if (cnt++) os << ", ";
    os << val;
  }
  return os << "]";
}
template <typename T>
inline ostream &operator<<(ostream &os, const set<T> &v) {
  os << "{";
  int cnt = 0;
  for (auto &val : v) {
    if (cnt++) os << ", ";
    os << val;
  }
  return os << "}";
}
template <typename T>
inline ostream &operator<<(ostream &os, const multiset<T> &v) {
  os << "{";
  int cnt = 0;
  for (auto &val : v) {
    if (cnt++) os << ", ";
    os << val;
  }
  return os << "}";
}
template <typename T1, typename T2>
inline ostream &operator<<(ostream &os, const map<T1, T2> &v) {
  os << "[";
  int cnt = 0;
  for (auto &val : v) {
    if (cnt++) os << ", ";
    os << val;
  }
  return os << "]";
}
template <typename Arg1>
void __f(const char *name, Arg1 &&arg1) {
  cerr << name << ": " << arg1 << endl;
}
template <typename Arg1, typename... Args>
void __f(const char *names, Arg1 &&arg1, Args &&...args) {
  const char *comma = strchr(names + 1, ',');
  cerr.write(names, comma - names) << ": " << arg1 << " |";
  __f(comma + 1, args...);
}
using ll = long long;
using ull = unsigned long long;
using vi = vector<int>;
using vll = vector<long long>;
using vvi = vector<vector<int>>;
using vs = vector<string>;
using vb = vector<bool>;
using vvb = vector<vector<bool>>;
using vc = vector<char>;
using si = set<int>;
using mpii = map<int, int>;
using pii = pair<int, int>;
using pll = pair<ll, ll>;
const int dx[] = {-1, 1, 0, 0};
const int dy[] = {0, 0, 1, -1};
template <class T>
inline bool umin(T &a, const T b) {
  return b < a ? a = b, 1 : 0;
}
template <class T>
inline bool umax(T &a, const T b) {
  return a < b ? a = b, 1 : 0;
}
struct SegmentTree {
  struct data {
    int mi, ma;
    ll sum;
    data() {}
    data(int _mi, int _ma, ll _sum) : mi(_mi), ma(_ma), sum(_sum) {}
  };
  struct node {
    int l, r;
    int lazy;
    data val;
    node() {}
  } t[200004 << 2];
  SegmentTree() {}
  void build(int id, int l, int r, vi &a) {
    t[id].l = l;
    t[id].r = r;
    t[id].lazy = 0;
    if (l == r) {
      t[id].val = data(a[l], a[l], a[l]);
    } else {
      int mid = (l + r) >> 1;
      build((id << 1), l, mid, a);
      build(((id << 1) | 1), mid + 1, r, a);
      t[id].val = merge(t[(id << 1)].val, t[((id << 1) | 1)].val);
    }
  }
  void apply(int id, int ma) {
    t[id].lazy = ma;
    ll len = t[id].r - t[id].l + 1;
    t[id].val = data(ma, ma, len * ma);
  }
  void pushDown(int id) {
    assert(t[id].l != t[id].r);
    if (t[id].lazy > 0) {
      apply((id << 1), t[id].lazy);
      apply(((id << 1) | 1), t[id].lazy);
    }
    t[id].lazy = 0;
  }
  data merge(const data &ld, const data &rd) {
    assert(ld.ma >= ld.mi);
    assert(rd.ma >= rd.mi);
    assert(ld.mi >= rd.ma);
    return data(min(ld.mi, rd.mi), max(ld.ma, rd.ma), ld.sum + rd.sum);
  }
  void updateMax(int id, int l, int r, int ma) {
    if (t[id].l == t[id].r) {
      assert(t[id].val.mi == t[id].val.ma);
      assert(t[id].val.mi == t[id].val.sum);
      int newVal = max(t[id].val.ma, ma);
      t[id].val = data(newVal, newVal, 1LL * newVal);
      return;
    }
    if (t[id].l == l && t[id].r == r) {
      if (ma >= t[id].val.ma) {
        apply(id, ma);
      } else if (ma >= t[id].val.mi) {
        pushDown(id);
        int mid = (t[id].l + t[id].r) >> 1;
        updateMax((id << 1), l, mid, ma);
        updateMax(((id << 1) | 1), mid + 1, r, ma);
        t[id].val = merge(t[(id << 1)].val, t[((id << 1) | 1)].val);
      }
      return;
    }
    pushDown(id);
    int mid = (t[id].l + t[id].r) >> 1;
    if (r <= mid)
      updateMax((id << 1), l, r, ma);
    else if (l > mid)
      updateMax(((id << 1) | 1), l, r, ma);
    else {
      updateMax((id << 1), l, mid, ma);
      updateMax(((id << 1) | 1), mid + 1, r, ma);
    }
    t[id].val = merge(t[(id << 1)].val, t[((id << 1) | 1)].val);
  }
  void query(int id, int l, int r, ll &had, int &got) {
    if (t[id].l == t[id].r) {
      assert(t[id].val.mi == t[id].val.ma);
      assert(t[id].val.mi == t[id].val.sum);
      if (had >= t[id].val.sum) {
        had -= t[id].val.sum;
        got += t[id].r - t[id].l + 1;
      }
      return;
    }
    if (t[id].l == l && t[id].r == r) {
      if (had >= t[id].val.sum) {
        had -= t[id].val.sum;
        got += t[id].r - t[id].l + 1;
      } else if (had >= t[id].val.mi) {
        pushDown(id);
        int mid = (t[id].l + t[id].r) >> 1;
        query((id << 1), l, mid, had, got);
        query(((id << 1) | 1), mid + 1, r, had, got);
      }
      return;
    }
    pushDown(id);
    int mid = (t[id].l + t[id].r) >> 1;
    if (r <= mid)
      query((id << 1), l, r, had, got);
    else if (l > mid)
      query(((id << 1) | 1), l, r, had, got);
    else {
      query((id << 1), l, mid, had, got);
      query(((id << 1) | 1), mid + 1, r, had, got);
    }
  }
} st;
int n, m;
void solve() {
  vi a(n + 1, 0);
  for (int i = 1; i <= n; i++) cin >> a[i];
  st.build(1, 1, n, a);
  while (m--) {
    int op, pos, val;
    cin >> op >> pos >> val;
    if (op == 1) {
      st.updateMax(1, 1, pos, val);
    } else if (op == 2) {
      ll had = val;
      int got = 0;
      st.query(1, pos, n, had, got);
      cout << got << endl;
    }
  }
}
void solve(int _cas) { solve(); }
int main() {
  srand(time(NULL));
  ios_base::sync_with_stdio(false);
  cin.tie(NULL), cout.tie(NULL), cout.precision(12);
  while (cin >> n >> m) solve(1);
}
