// Slower C++ solution:
#include <bits/stdc++.h>



using namespace std;



struct point

{

	int x, y, id;

} p[100005];



vector< pair<int, pair<int, int> > > q;



bool cmpx(point a, point b)

{

	if (a.x != b.x) return a.x > b.x;

	else return a.y > b.y;

}



bool cmpy(point a, point b)

{

	if (a.y != b.y) return a.y > b.y;

	else return a.x > b.x;

}



int up[100005];



void makesets()

{

	for (int i = 0; i < 100001; i++)

	{

		up[i] = -1;

	}

}



int Find(int x)

{

	if (up[x] < 0) return x;

	int root = Find(up[x]);

	up[x] = root;

	return root;

}



void Union(int x, int y)

{

	if (Find(x) == Find(y)) return;

	if (up[x] < up[y])

	{

		up[x] += up[y];

		up[y] = x;

	}

	else

	{

		up[y] += up[x];

		up[x] = y;

	}

}



int n;



signed main()

{

	scanf("%d", &n);

	for (int i = 1; i <= n; i++)

	{

		scanf("%d%d", &p[i].x, &p[i].y);

		p[i].id = i;

	}

	sort(p+1, p+1+n, cmpx);

	for (int i = 1; i < n; i++)

	{

		q.push_back(make_pair(p[i].x - p[i+1].x, make_pair(p[i].id, p[i+1].id)));

	}

	sort(p+1, p+1+n, cmpy);

	for (int i = 1; i < n; i++)

	{

		q.push_back(make_pair(p[i].y - p[i+1].y, make_pair(p[i].id, p[i+1].id)));

	}

	sort(q.begin(), q.end());

	makesets();

	long long res = 0;

	for (int i = 0; i < q.size(); i++)

	{

		int u = q[i].second.first, v = q[i].second.second;

		if (Find(u) != Find(v))

		{

			Union(Find(u), Find(v));

			res += q[i].first;

		}

	}

	printf("%lld", res);

}

// Faster C++ solution for the same problem (measured speedup: 1.394597626267652x):
#include <bits/stdc++.h>





using namespace std;



typedef long long int llint;

#define abs absolute



struct node

{

    llint x, y, id;

};



struct edge

{

    llint start, end, weight;

};



inline llint absolute (llint a)

{

    return (a > 0) ? a : (- a);

}



inline bool x_asc (node a, node b)

{

    return (a.x < b.x);

}



inline bool y_asc (node a, node b)

{

    return (a.y < b.y);

}



inline bool weight_asc (edge a, edge b)

{

    return (a.weight < b.weight);

}



inline llint ancestor_recursive_search (vector <llint>& parent, llint id)

{

    // find ancestors recursively

    if (parent[id] != id) parent[id] = ancestor_recursive_search(parent, parent[id]);

    return parent[id];

}



int main(int argc, char const *argv[])

{

    llint length; cin >> length;

    vector <node> city (length);

    for (llint i = 0 ; i <= length - 1 ; i++)

    {

        cin >> city[i].x >> city[i].y; city[i].id = i;

    };

    

    // sort by x-diff to compute sides from x-diff



    sort (city.begin(), city.end(), x_asc);

    vector <edge> roads;

    for (llint i = 0 ; i <= length - 2 ; i++)

    {

        edge tmp;

        tmp.start = city[i].id; tmp.end = city[i + 1].id;

        tmp.weight = abs(city[i].x - city[i + 1].x);

        roads.push_back(tmp);

    };



    // sort by Y-diff to compute sides from y-diff



    sort (city.begin(), city.end(), y_asc);

    for (llint i = 0 ; i <= length - 2 ; i++)

    {

        edge tmp;

        tmp.start = city[i].id; tmp.end = city[i + 1].id;

        tmp.weight = abs(city[i].y - city[i + 1].y);

        roads.push_back(tmp);

    };



    // parent record to compute MST



    vector <llint> parent (length);

    for (llint i = 0 ; i <= length - 1 ; i++) parent[i] = i;



    // sort sides for easier computation



    sort(roads.begin(), roads.end(), weight_asc);



    // MST computation from sides formed from both sources (x-diff and y-diff)



    llint out = 0;

    for (edge i : roads)

    {   

        // find both vertices' ancestor(s)

        llint start_vertex_ancestor = ancestor_recursive_search(parent, i.start), end_vertex_ancestor = ancestor_recursive_search(parent, i.end);



        // if they're not identical

        // then add to MST

        if (start_vertex_ancestor != end_vertex_ancestor)

        {

            // add to total weight

            out += i.weight;

            // and rewrite parent record

            parent[end_vertex_ancestor] = start_vertex_ancestor;

        }

    };



    cout << out;

}