#include <bits/stdc++.h>
using namespace std;
template <class T>
inline void smin(T &a, T b) {
  if (a > b) a = b;
}
template <class T>
inline void smax(T &a, T b) {
  if (a < b) a = b;
}
pair<int, int> p[1111 * 11], q[1111 * 11];
char grid[1111][1111];
pair<int, int> O;
int sgn(int a) { return a < 0 ? -1 : a > 0; }
pair<int, int> operator-(pair<int, int> a, pair<int, int> b) {
  return pair<int, int>(a.first - b.first, a.second - b.second);
}
int multi(pair<int, int> a, pair<int, int> b) {
  return a.first * b.second - a.second * b.first;
}
int dist(pair<int, int> a, pair<int, int> b) {
  return ((a.first - b.first) * (a.first - b.first)) +
         ((a.second - b.second) * (a.second - b.second));
}
bool cmp(pair<int, int> a, pair<int, int> b) {
  int t = sgn(multi(a - O, b - O));
  if (t) return t > 0;
  return dist(a, O) < dist(b, O);
}
void graham(pair<int, int> *p, int n, pair<int, int> *h, int &m) {
  int i;
  if (n <= 3) {
    for (i = 0; i < n; i++) h[i] = p[i];
    m = n;
    return;
  }
  for (i = 1; i < n; i++) {
    if (p[i].second < p[0].second ||
        sgn(p[i].second - p[i].second) == 0 && p[i].first < p[0].first)
      swap(p[i], p[0]);
  }
  O = p[0], sort(p + 1, p + n, cmp);
  m = 2, h[0] = p[0], h[1] = p[1];
  for (i = 2; i < n; i++) {
    while (m > 1 && sgn(multi(p[i] - h[m - 2], h[m - 1] - h[m - 2])) >= 0) m--;
    h[m++] = p[i];
  }
}
int main() {
  int N, i, j, first, second, np, m;
  while (scanf("%d", &N) && N) {
    for (i = N - 1; i >= 0; i--) scanf("%s", grid[i]);
    np = 0;
    for (i = 0; i < N; i++) {
      for (j = 0; j < N; j++) {
        if (grid[i][j] != '1') continue;
        first = j, second = i;
        if (i && j) {
          if (grid[i - 1][j] > '0' && grid[i - 1][j - 1] > '0' &&
              grid[i][j - 1] > '0')
            p[np++] = pair<int, int>(first, second);
        }
        if (i && j < N - 1) {
          if (grid[i - 1][j] > '0' && grid[i - 1][j + 1] > '0' &&
              grid[i][j + 1] > '0')
            p[np++] = pair<int, int>(first + 1, second);
        }
        if (i < N - 1 && j < N - 1) {
          if (grid[i + 1][j + 1] > '0' && grid[i + 1][j] > '0' &&
              grid[i][j + 1] > '0')
            p[np++] = pair<int, int>(first + 1, second + 1);
        }
        if (i < N - 1 && j) {
          if (grid[i + 1][j] > '0' && grid[i + 1][j - 1] > '0' &&
              grid[i][j - 1] > '0')
            p[np++] = pair<int, int>(first, second + 1);
        }
      }
    }
    sort(p, p + np);
    np = unique(p, p + np) - p;
    graham(p, np, q, m);
    if (sgn(multi(q[2] - q[0], q[1] - q[0]) < 0))
      for (i = 0; i < m / 2; i++) swap(q[i], q[m - 1 - i]);
    printf("%d\n\n", m);
    int cnt = 0;
    pair<int, int> mid = q[0];
    for (i = 1; i < m; i++) {
      if (mid > q[i]) mid = q[i], cnt = i;
    }
    for (i = cnt; i < m; i++) {
      printf("%d %d\n\n", q[i].first, q[i].second);
    }
    for (i = 0; i < cnt; i++) {
      printf("%d %d\n\n", q[i].first, q[i].second);
    }
  }
  return 0;
}
