#include <bits/stdc++.h>
using namespace std;
const int RLEN = 1 << 20 | 1;
inline char gc() {
  static char ibuf[RLEN], *ib, *ob;
  (ob == ib) && (ob = (ib = ibuf) + fread(ibuf, 1, RLEN, stdin));
  return (ob == ib) ? EOF : *ib++;
}
inline int read() {
  char ch = getchar();
  int res = 0, f = 1;
  while (!isdigit(ch)) f ^= ch == '-', ch = getchar();
  while (isdigit(ch)) res = (res + (res << 2) << 1) + (ch ^ 48), ch = getchar();
  return f ? res : -res;
}
inline void chemx(int &a, int b) { a < b ? a = b : 0; }
inline void chemn(int &a, int b) { a > b ? a = b : 0; }
const int N = 150005;
const int C = 11;
struct Val {
  int val, siz;
  friend inline bool operator<(const Val &a, const Val &b) {
    return a.siz > b.siz;
  }
};
int n, q, a[N], S, P;
struct node {
  int len;
  Val v[C];
  node() { len = 0; }
  inline void init(int val, int siz) {
    len = 1, v[1].val = val, v[1].siz = siz;
  }
  friend inline node operator+(const node &a, const node &b) {
    node c = a;
    for (int i = 1; i <= b.len; i++) {
      bool fg = 0;
      for (int j = 1; j <= c.len; j++)
        if (b.v[i].val == c.v[j].val) {
          c.v[j].siz += b.v[i].siz, fg = 1;
        }
      if (!fg) c.v[++c.len] = b.v[i];
    }
    if (c.len > S) {
      sort(c.v + 1, c.v + c.len + 1);
      for (int i = c.len; i > S; i--)
        for (int j = 1; j <= i; j++) c.v[j].siz -= c.v[i].siz;
      while (c.len && c.v[c.len].siz <= 0) c.len--;
    }
    return c;
  }
};
namespace Seg {
node tr[N << 2];
int tag[N << 2];
inline void pushup(int u) { tr[u] = tr[(u << 1)] + tr[((u << 1) | 1)]; }
inline void pushnow(int u, int l, int r, int k) {
  tag[u] = k, tr[u].init(k, r - l + 1);
}
inline void pushdown(int u, int l, int r) {
  if (!tag[u]) return;
  pushnow((u << 1), l, ((l + r) >> 1), tag[u]);
  pushnow(((u << 1) | 1), ((l + r) >> 1) + 1, r, tag[u]);
  tag[u] = 0;
}
void build(int u, int l, int r) {
  if (l == r) {
    tr[u].init(a[l], 1);
    return;
  }
  build((u << 1), l, ((l + r) >> 1)),
      build(((u << 1) | 1), ((l + r) >> 1) + 1, r);
  pushup(u);
}
void update(int u, int l, int r, int st, int des, int k) {
  if (st <= l && r <= des) return pushnow(u, l, r, k);
  pushdown(u, l, r);
  if (st <= ((l + r) >> 1)) update((u << 1), l, ((l + r) >> 1), st, des, k);
  if (((l + r) >> 1) < des)
    update(((u << 1) | 1), ((l + r) >> 1) + 1, r, st, des, k);
  pushup(u);
}
node query(int u, int l, int r, int st, int des) {
  if (st <= l && r <= des) return tr[u];
  pushdown(u, l, r);
  node res;
  if (des <= ((l + r) >> 1))
    res = query((u << 1), l, ((l + r) >> 1), st, des);
  else if (((l + r) >> 1) < st)
    res = query(((u << 1) | 1), ((l + r) >> 1) + 1, r, st, des);
  else
    res = query((u << 1), l, ((l + r) >> 1), st, des) +
          query(((u << 1) | 1), ((l + r) >> 1) + 1, r, st, des);
  pushup(u);
  return res;
}
}  // namespace Seg
int main() {
  n = read(), q = read(), P = read(), S = 100 / P;
  for (int i = 1; i <= n; i++) a[i] = read();
  Seg::build(1, 1, n);
  while (q--) {
    int op = read(), l = read(), r = read();
    if (op == 1) {
      int id = read();
      Seg::update(1, 1, n, l, r, id);
    } else {
      node res = Seg::query(1, 1, n, l, r);
      cout << res.len << " ";
      for (int i = 1; i <= res.len; i++) cout << res.v[i].val << " ";
      puts("");
    }
  }
}
