1
# Runtime: 2311 ms (Top 90.13%) | Memory: 73.8 MB (Top 86.18%)3
* Make groups of nodes which are connected4
eg., edges = [[0,2],[0,5],[2,4],[1,6],[5,4]]11
groups will be {0: 4, 1: 2, 3: 1},12
i.e 4 nodes are present in group0, 2 nodes are present in group1 and 1 node is present in group314
* Now, we have [4, 2, 1] as no of nodes in each group, we have to multiply each of no. with remaining15
ans = (4 * 2 + 4 * 1) + (2 * 1)16
but calculating ans this way will give TLE.18
* if we notice, (4 * 2 + 4 * 1) + (2 * 1), we can combine, equation like this,19
4 * 2 + (4 + 2) * 1, using this, we can reduce complexity.20
so, if we have count of groups array as [a, b, c, d], ans will be,21
ans = a * b + (a + b) * c + (a + b + c) * d23
* will use, union for generating groups.24
* ps, you can modify UnionFind class as per your need. Have implemented full union-find for beginners.29
def __init__(self, size):30
self.root = [i for i in range(size)]31
self.rank = [1] * size36
self.root[x] = self.find(self.root[x])39
def union(self, x, y):43
if self.rank[rootX] > self.rank[rootY]:44
self.root[rootY] = rootX45
elif self.rank[rootX] < self.rank[rootY]:46
self.root[rootX] = rootY48
self.root[rootY] = rootX53
def countPairs(self, n: int, edges: List[List[int]]) -> int:57
C = Counter([dsu.find(i) for i in range(n)])58
groupCounts = list(C.values())60
firstGroupCount = groupCounts[0]61
for i in range(1, len(groupCounts)):62
ans += firstGroupCount * groupCounts[i]63
firstGroupCount += groupCounts[i]