#include <bits/stdc++.h>
using namespace std;
struct Node {
  Node* c[2];
  int count;
  Node(Node* l, Node* r) : c{l, r}, count(0) {}
  Node() : Node(nullptr, nullptr) {}
  Node* go(int i) {
    if (c[i] == nullptr) c[i] = new Node();
    return c[i];
  }
};
Node root = Node();
int scr[2][32];
void toscr(int x, int A[32]) {
  for (int i = 31; i >= 0; i--, x >>= 1) A[i] = x & 1;
}
void upd(int x, int inc) {
  toscr(x, scr[0]);
  Node* curr = &root;
  for (int i = 0; i < 32; i++) {
    curr = curr->go(scr[0][i]);
    curr->count += inc;
  }
}
void add(int x) { upd(x, 1); }
void rem(int x) { upd(x, -1); }
int query(int p, int l) {
  toscr(p, scr[0]);
  toscr(l, scr[1]);
  int cnt = 0;
  Node* curr = &root;
  for (int i = 0; i < 32; i++) {
    if (scr[1][i]) {
      cnt += curr->go(0 ^ scr[0][i])->count;
      curr = curr->go(1 ^ scr[0][i]);
    } else
      curr = curr->go(0 ^ scr[0][i]);
  }
  return cnt;
}
int main() {
  ios_base::sync_with_stdio(false);
  cin.tie(NULL);
  cout.tie(NULL);
  int q;
  cin >> q;
  for (int i = 0; i < q; i++) {
    int ty, p, l;
    cin >> ty >> p;
    switch (ty) {
      case 1:
        add(p);
        break;
      case 2:
        rem(p);
        break;
      case 3:
        cin >> l;
        cout << query(p, l) << '\n';
        break;
      default:
        break;
    }
  }
  return 0;
}
