#include <bits/stdc++.h>
using namespace std;
constexpr int MAXN = 1 << 18;
int par[MAXN];
int sz[MAXN];
vector<pair<int, int>> history;
void init() {
  iota(par, par + MAXN, 0);
  fill(sz, sz + MAXN, 1);
}
int find(int v) { return v == par[v] ? v : find(par[v]); }
int merge(int v, int u) {
  v = find(v);
  u = find(u);
  if (v == u) {
    return 0;
  }
  if (sz[v] > sz[u]) {
    swap(v, u);
  }
  par[v] = u;
  sz[u] += sz[v];
  history.emplace_back(u, v);
  return 1;
}
void rollback() {
  auto [u, v] = history.back();
  history.pop_back();
  par[v] = v;
  sz[u] -= sz[v];
}
int N, Q, B = 1;
map<pair<int, int>, vector<int>> pos;
set<pair<int, int>> curr;
tuple<int, int, int> query[MAXN];
vector<pair<int, int>> seg[2 * MAXN];
void addEdge(int v, int u, int l, int r) {
  for (l += B, r += B; l < r; l >>= 1, r >>= 1) {
    if (l & 1) {
      seg[l++].emplace_back(v, u);
    }
    if (r & 1) {
      seg[--r].emplace_back(v, u);
    }
  }
}
int lastAns = 0;
void solve(int l, int r, int p) {
  int op = 0;
  for (auto [v, u] : seg[p]) {
    op += merge(v, u);
  }
  if (l == r - 1) {
    auto [v1, u1, t] = query[l];
    int v2 = v1 % N + 1;
    int u2 = u1 % N + 1;
    if (v2 > u2) {
      swap(v2, u2);
    }
    if (lastAns) {
      swap(v1, v2);
      swap(u1, u2);
    }
    if (t == 1) {
      auto it1 = curr.emplace(v1, u1);
      if (it1.second) {
        auto it = upper_bound(pos[{v1, u1}].begin(), pos[{v1, u1}].end(), l);
        int P = it == pos[{v1, u1}].end() ? B : *it;
        addEdge(v1, u1, l + 1, P);
      } else {
        curr.erase(it1.first);
      }
      auto it2 = curr.emplace(v2, u2);
      if (it2.second) {
        curr.erase(it2.first);
      } else {
        auto it = upper_bound(pos[{v2, u2}].begin(), pos[{v2, u2}].end(), l);
        int P = it == pos[{v2, u2}].end() ? B : *it;
        addEdge(v2, u2, l + 1, P);
      }
    } else if (t == 2) {
      lastAns = find(v1) == find(u1);
      cout << lastAns;
    }
  } else {
    int m = (l + r) / 2;
    solve(l, m, 2 * p);
    solve(m, r, 2 * p + 1);
  }
  for (int i = 0; i < op; i++) {
    rollback();
  }
}
int main() {
  ios::sync_with_stdio(false);
  cin >> N >> Q;
  for (int i = 0; i < Q; i++) {
    int t, v1, u1;
    cin >> t >> v1 >> u1;
    if (v1 > u1) {
      swap(v1, u1);
    }
    query[i] = make_tuple(v1, u1, t);
    if (t == 1) {
      pos[{v1, u1}].push_back(i);
      int v2 = v1 % N + 1;
      int u2 = u1 % N + 1;
      if (v2 > u2) {
        swap(v2, u2);
      }
      pos[{v2, u2}].push_back(i);
    }
  }
  init();
  while (B < Q) {
    B <<= 1;
  }
  solve(0, B, 1);
  return 0;
}
