Most Stones Removed with Same Row or Column

Max stones removable while keeping each connected component non-empty — DSU on row/column unions.

Medium
Time O(N * α(N)) Space O(N)
LeetCode
4 min read
union-find graph

Problem#

There are stones placed on a grid at given coordinates. A stone can be removed if it shares a row or column with another remaining stone. Return the maximum number of stones you can remove.

Examples#

  • stones = [[0,0],[0,1],[1,0],[1,2],[2,1],[2,2]]5.
  • stones = [[0,0],[0,2],[1,1],[2,0],[2,2]]3.

Constraints#

  • 1 <= stones.length <= 1000, 0 <= stones[i].x, stones[i].y <= 10^4.

Hints#

Hint 1
In each connected component, you can remove all but one stone.
Hint 2
Answer = n - #components. Union stones sharing a row or column.

Approach#

Treat each row and each column as a DSU node (offset columns by +10000 to avoid collision). Union each stone’s row with its column. The answer is n - #distinct roots.

Solution#

Most Stones Removed with Same Row or Column
class Solution {
unordered_map<int,int> parent;
int find(int x) {
if (!parent.count(x)) parent[x] = x;
while (parent[x] != x) { parent[x] = parent[parent[x]]; x = parent[x]; }
return x;
}
void unite(int a, int b) { parent[find(a)] = find(b); }
public:
int removeStones(vector<vector<int>>& stones) {
for (auto& s : stones) unite(s[0], s[1] + 10001);
unordered_set<int> roots;
for (auto& s : stones) roots.insert(find(s[0]));
return stones.size() - roots.size();
}
};

Editorial#

The clever model: union the row index with the column index (offset). Two stones end up in the same component iff a chain of row/column shares connects them. In any component of k stones we can remove k - 1 (peel off all but the last). Total removable = n - #components.

Complexity#

  • Time: O(N * α(N)).
  • Space: O(N).

Concept revision#

Search ESC

Keyboard shortcuts

Shortcuts are disabled while typing in inputs.