#include using namespace std; void addEdges(vector> & g, const vector> & v) { int i = 0, j = 0; while(j < v.size()-1) { j++; if(v[i].first == v[j].first) { g[v[i].second].push_back(v[j].second); g[v[j].second].push_back(v[i].second); } else { i=j; } } } int main() { int N; cin >> N; vector> y(N), x(N); for(int i = 0; i < N; i++) { x[i].second = i; y[i].second = i; cin >> x[i].first >> y[i].first; } vector> g(N); sort(x.begin(), x.end()); sort(y.begin(), y.end()); addEdges(g,x); addEdges(g,y); vector seen(N, false); int result = 0; queue q; for(int i = 0; i < N; i++) { if(!seen[i]) { result++; seen[i] = true; q.push(i); while(!q.empty()) { for(auto a : g[q.front()]) { if(!seen[a]) { seen[a] = true; q.push(a); } } q.pop(); } } } cout << result -1 << '\n'; }