#include <bits/stdc++.h>
using namespace std;
const int MAXN = -1;
struct linea {
  int cnt;
  string B;
  char &operator[](int v) { return B[v]; }
};
struct rta {
  int a, b, c;
  rta(int a = 0, int b = 0, int c = 0) : a(a), b(b), c(c) {}
};
int n;
vector<linea> Col;
vector<rta> ans;
void swap_row(int u, int v) {
  if (u == v) return;
  for (int i = (0); i < (int)(n); i++) swap(Col[i][u], Col[i][v]);
  ans.push_back(rta(1, u, v));
}
void swap_col(int u, int v) {
  if (u == v) return;
  swap(Col[u], Col[v]);
  ans.push_back(rta(2, u, v));
}
void acomoda(int n, int m) {
  int id = n - m - 1;
  int p = 0;
  for (int i = (id + 1); i < (int)(n); i++) {
    if (Col[id][i] == '*') continue;
    while (Col[id][p] == '.') p++;
    swap_row(p, i);
  }
}
int main() {
  while (cin >> n) {
    ans.clear();
    Col.resize(n);
    for (int i = (0); i < (int)(n); i++) Col[i].B.resize(n), Col[i].cnt = 0;
    for (int i = (0); i < (int)(n); i++)
      for (int j = (0); j < (int)(n); j++) Col[i][j] = '.';
    for (int i = (0); i < (int)(n - 1); i++) {
      int x, y;
      cin >> x >> y;
      Col[y - 1][x - 1] = '*';
      Col[y - 1].cnt++;
    }
    while (1) {
      int m = 2000, id;
      for (int i = (0); i < (int)(n); i++)
        if (Col[i].cnt <= m && Col[i].cnt) {
          m = Col[i].cnt;
          id = i;
        }
      if (m == 2000) break;
      swap_col(id, n - m - 1);
      int p = 0;
      for (int i = (n - m); i < (int)(n); i++) {
        if (!(Col[i].cnt)) continue;
        while (Col[p].cnt) p++;
        swap_col(p, i);
      }
      acomoda(n, m);
      n -= m;
      while (Col.size() > n) Col.pop_back();
      for (int i = (0); i < (int)(n); i++) {
        while (Col[i].B.size() > n) {
          if (Col[i].B.back() == '*') Col[i].cnt--;
          Col[i].B.pop_back();
        }
      }
    }
    cout << ans.size() << endl;
    for (int i = (0); i < (int)(ans.size()); i++) {
      printf("%d %d %d\n", ans[i].a, ans[i].b + 1, ans[i].c + 1);
    }
  }
  return 0;
}
