#include <bits/stdc++.h>
using namespace std;
const int oo = 0x3f3f3f3f;
const long long ooo = 9223372036854775807ll;
const int _cnt = 1000 * 1000 + 7;
const int _p = 1000 * 1000 * 1000 + 7;
const int N = 100105;
const double PI = acos(-1.0);
const double eps = 1e-9;
int o(int x) { return x % _p; }
int gcd(int a, int b) { return b ? gcd(b, a % b) : a; }
int lcm(int a, int b) { return a / gcd(a, b) * b; }
void file_put() {
  freopen("filename.in", "r", stdin);
  freopen("filename.out", "w", stdout);
}
int n, m, a[N], l, r, x, op, h[450][N], cnt[450][N], B, T, L[450], R[450],
    LL[450], RR[450], off[450], ans = 0;
int _find(int k, int x) {
  return (!h[k][x] || h[k][x] == x) ? h[k][x] = x : h[k][x] = _find(k, h[k][x]);
}
int query(int k, int l, int r, int x) {
  int ans = 0;
  for (int i = (l); i <= (r); ++i) a[i] = _find(k, a[i]);
  for (int i = (l); i <= (r); ++i) ans += (a[i] - off[k] == x);
  return ans;
}
int query(int k, int x) {
  if (LL[k] - off[k] >= x || RR[k] - off[k] < x) return 0;
  return cnt[k][x + off[k]];
}
void update(int k, int l, int r, int x) {
  for (int i = (l); i <= (r); ++i) a[i] = _find(k, a[i]);
  for (int i = (l); i <= (r); ++i)
    if (a[i] - off[k] > x) {
      cnt[k][a[i]]--;
      a[i] -= x;
      cnt[k][a[i]]++;
    }
}
void update(int k, int x) {
  if (RR[k] - LL[k] < x) return;
  if (RR[k] - LL[k] >= 2 * x) {
    for (int i = (LL[k]); i <= (LL[k] + x); ++i) {
      h[k][i] = i + x;
      ;
      cnt[k][i + x] += cnt[k][i];
      cnt[k][i] = 0;
    }
    cnt[k][LL[k] += x] = 0;
    off[k] += x;
  } else {
    for (int i = (RR[k]); i >= (LL[k] + x + 1); --i) {
      h[k][i] = i - x;
      cnt[k][i - x] += cnt[k][i];
      cnt[k][i] = 0;
    }
    RR[k] = LL[k] + x;
  }
}
int main() {
  scanf("%d%d", &n, &m);
  B = sqrt(1.0 * n) + 1, T = (n - 1) / B;
  for (int i = (0); i <= (n - 1); ++i) scanf("%d", &a[i]), cnt[i / B][a[i]]++;
  for (int i = (0); i <= (T); ++i)
    L[i] = i * B, R[i] = (i + 1) * B - 1, RR[i] = 100000;
  while (m--) {
    scanf("%d%d%d%d", &op, &l, &r, &x);
    l--, r--;
    if (op == 1) {
      if (l / B == r / B)
        update(l / B, l, r, x);
      else {
        update(l / B, l, R[l / B], x);
        update(r / B, L[r / B], r, x);
        for (int i = (l / B + 1); i <= (r / B - 1); ++i) update(i, x);
      }
    }
    if (op == 2) {
      ans = 0;
      if (l / B == r / B)
        ans += query(l / B, l, r, x);
      else {
        ans += query(l / B, l, R[l / B], x);
        ans += query(r / B, L[r / B], r, x);
        for (int i = (l / B + 1); i <= (r / B - 1); ++i) ans += query(i, x);
      }
      printf("%d\n", ans);
    }
  }
  return 0;
}
