62. Number of Provinces
isConnected[i][j] = 1 means cities i and j are directly connected. A province is a group of cities connected directly or indirectly. Return the number of provinces.
Example 1
isConnected = [[1,1,0],[1,1,0],[0,0,1]]2Example 2
isConnected = [[1,0,0],[0,1,0],[0,0,1]]3Hint 1
Count connected components.
Hint 2
Union-Find: start with n groups and decrease the count on every successful union.
Approach 1: DFS per component
Start a DFS from each unvisited city.
Approach 2: Union-Find ✅
Union connected pairs; count successful unions.
Reference solution for Union-Find (time O(n² · α), space O(n)). Each solution passes every test in all four languages.
class Solution:
def findCircleNum(self, isConnected: List[List[int]]) -> int:
n = len(isConnected)
parent = list(range(n))
def find(x): # with path compression
while parent[x] != x:
parent[x] = parent[parent[x]]
x = parent[x]
return x
groups = n
for i in range(n):
for j in range(i + 1, n):
if isConnected[i][j]:
a, b = find(i), find(j)
if a != b:
parent[a] = b # union two provinces
groups -= 1
return groupsclass Solution {
private int[] parent;
private int find(int x) {
while (parent[x] != x) { parent[x] = parent[parent[x]]; x = parent[x]; }
return x;
}
public int findCircleNum(int[][] isConnected) {
int n = isConnected.length, groups = n;
parent = new int[n];
for (int i = 0; i < n; i++) parent[i] = i;
for (int i = 0; i < n; i++)
for (int j = i + 1; j < n; j++)
if (isConnected[i][j] == 1) {
int a = find(i), b = find(j);
if (a != b) { parent[a] = b; groups--; }
}
return groups;
}
}class Solution {
vector<int> parent;
int find(int x) {
while (parent[x] != x) { parent[x] = parent[parent[x]]; x = parent[x]; }
return x;
}
public:
int findCircleNum(vector<vector<int>>& isConnected) {
int n = isConnected.size(), groups = n;
parent.resize(n);
iota(parent.begin(), parent.end(), 0);
for (int i = 0; i < n; i++)
for (int j = i + 1; j < n; j++)
if (isConnected[i][j]) {
int a = find(i), b = find(j);
if (a != b) { parent[a] = b; groups--; }
}
return groups;
}
};function findCircleNum(isConnected) {
const n = isConnected.length, parent = [...Array(n).keys()];
const find = x => { while (parent[x] !== x) { parent[x] = parent[parent[x]]; x = parent[x]; } return x; };
let groups = n;
for (let i = 0; i < n; i++)
for (let j = i + 1; j < n; j++)
if (isConnected[i][j]) {
const a = find(i), b = find(j);
if (a !== b) { parent[a] = b; groups--; }
}
return groups;
}Try solving it yourself first. Interviewers care more about how you explain the approach than about the finished code.
Watch the core idea of this problem step by step. Change the input and press Visualize.
Explained in the lesson Topological Sort, Dijkstra & Union-Find.
Run your code to see results here.