#include <bits/stdc++.h>
using namespace std;
struct Point {
  int x, y;
};
bool vis[20][20];
int dx[] = {-1, -1, -1, 0, 0, 1, 1, 1};
int dy[] = {-1, 0, 1, -1, 1, -1, 0, 1};
int ans3 = 0;
int abs(int a) { return a < 0 ? -a : a; }
void bfs(int x1, int y1, int x2, int y2) {
  memset(vis, false, sizeof(vis));
  Point tmp = (Point){x1, y1};
  queue<Point> nodequeue;
  while (!nodequeue.empty()) nodequeue.pop();
  nodequeue.push(tmp);
  nodequeue.push((Point){0, 0});
  while (!nodequeue.empty()) {
    tmp = nodequeue.front();
    vis[tmp.x][tmp.y] = true;
    nodequeue.pop();
    if (tmp.x == x2 && tmp.y == y2) return;
    if (tmp.x == 0 && tmp.y == 0) {
      ans3++;
      if (!nodequeue.empty()) nodequeue.push((Point){0, 0});
      continue;
    }
    for (int i = 0; i < 8; i++) {
      int tx = tmp.x + dx[i];
      int ty = tmp.y + dy[i];
      if (tx >= 1 && tx <= 8 && ty >= 1 && ty <= 8 && !vis[tx][ty]) {
        nodequeue.push((Point){tx, ty});
      }
    }
  }
  return;
}
int main() {
  int r1, c1, r2, c2;
  while (scanf("%d%d%d%d", &r1, &c1, &r2, &c2) != EOF) {
    ans3 = 0;
    bfs(r1, c1, r2, c2);
    int ans2;
    int flag1 = (r1 & 1) ^ (c1 & 1);
    int flag2 = (r2 & 1) ^ (c2 & 1);
    if (flag1 ^ flag2)
      ans2 = 0;
    else {
      if (abs(r2 - r1) == abs(c2 - c1))
        ans2 = 1;
      else
        ans2 = 2;
    }
    int ans1;
    if (r2 == r1 || c2 == c1)
      ans1 = 1;
    else
      ans1 = 2;
    printf("%d %d %d\n", ans1, ans2, ans3);
  }
  return 0;
}
