#include <bits/stdc++.h>
using namespace std;
int n;
vector<pair<int, int>> xs, ys;
struct UnionFind {
  vector<int> par_;
  vector<int> rank_;
  void init(int size) {
    par_.resize(size, 0);
    rank_.resize(size, 0);
    for (int i = 0; i < size; i++) {
      par_[i] = i;
      rank_[i] = 0;
    }
  }
  int root(int x) { return par_[x] == x ? x : par_[x] = root(par_[x]); }
  bool unite(int x, int y) {
    x = root(x);
    y = root(y);
    if (x == y) return true;
    if (rank_[x] < rank_[y]) {
      par_[x] = y;
    } else {
      par_[y] = x;
      if (rank_[x] == rank_[y]) rank_[x]++;
    }
    return false;
  }
  bool same(int x, int y) { return root(x) == root(y); }
};
int main() {
  cin >> n;
  xs.resize(n);
  ys.resize(n);
  for (int i = 0; i < n; i++) {
    int a, b;
    cin >> a >> b;
    xs.push_back(pair<int, int>(a, i));
    ys.push_back(pair<int, int>(b, i));
  }
  sort(xs.begin(), xs.end());
  sort(ys.begin(), ys.end());
  priority_queue<pair<int, pair<int, int>>, vector<pair<int, pair<int, int>>>,
                 greater<pair<int, pair<int, int>>>>
      que;
  for (int i = 0; i < xs.size() - 1; i++) {
    int i1 = xs[i].second;
    int i2 = xs[i + 1].second;
    que.push(pair<int, pair<int, int>>(abs(xs[i].first - xs[i + 1].first),
                                       pair<int, int>(i1, i2)));
  }
  for (int i = 0; i < ys.size() - 1; i++) {
    int i1 = ys[i].second;
    int i2 = ys[i + 1].second;
    que.push(pair<int, pair<int, int>>(abs(ys[i].first - ys[i + 1].first),
                                       pair<int, int>(i1, i2)));
  }
  UnionFind uf;
  uf.init(n);
  int c = 0;
  int res = 0;
  while (c < n - 1) {
    pair<int, pair<int, int>> p = que.top();
    que.pop();
    int a = p.second.first;
    int b = p.second.second;
    if (!uf.same(a, b)) {
      uf.unite(a, b);
      res += p.first;
      c++;
    }
  }
  cout << res << endl;
  return 0;
}
