cconnected.
Understand the pattern. Find your own way.Find your starting point
Your learning feed/Idea 72 of 218
Ideas this builds on
Graphs72 / 218

Making A Large Island

Picture

In [[1,1],[1,0]], the water square touches the same size-3 island from two directions. Flipping it gives size 4, not 7. The important neighbors are distinct components, not individual squares.

Predict

What is enough information to score a particular water square without rebuilding every island?

Walk through the small example

The distinct roots of its adjacent land components and their stored sizes. Add those sizes plus one for the newly created land square.

Mental model and complete Python solution

Flatten (r,c) into r*columns+c. Join neighboring land cells once. Union-find preserves component size at each root. For a candidate flip, at most four neighboring roots can contribute; a set prevents duplicate contributions from one wrapping island. Existing islands also remain candidates, which handles an all-land grid. Flood-fill component labels are an equally valid static preprocessing method; DSU is useful here to reuse the merge-and-summary model.

What the function promises: For a nonempty square binary grid, return the largest four-neighbor land component after changing at most one zero to one. The helper also handles rectangular and empty grids and does not mutate them.

class DisjointSet:
    def __init__(self, n):
        self.parent = list(range(n))
        self.size = [1] * n

    def find(self, x):
        while x != self.parent[x]:
            self.parent[x] = self.parent[self.parent[x]]
            x = self.parent[x]
        return x

    def union(self, a, b):
        a, b = self.find(a), self.find(b)
        if a == b:
            return False
        if self.size[a] < self.size[b]:
            a, b = b, a
        self.parent[b] = a
        self.size[a] += self.size[b]
        return True

def largest_island(grid):
    if not grid or not grid[0]:
        return 0
    rows, cols = len(grid), len(grid[0])
    groups = DisjointSet(rows * cols)
    for r in range(rows):
        for c in range(cols):
            if grid[r][c] == 1:
                for nr, nc in ((r-1, c), (r, c-1)):
                    if nr >= 0 and nc >= 0 and grid[nr][nc] == 1:
                        groups.union(r*cols+c, nr*cols+nc)
    best = 0
    for r in range(rows):
        for c in range(cols):
            if grid[r][c] == 1:
                best = max(best, groups.size[groups.find(r*cols+c)])
                continue
            roots = set()
            for nr, nc in ((r-1,c), (r+1,c), (r,c-1), (r,c+1)):
                if 0 <= nr < rows and 0 <= nc < cols and grid[nr][nc] == 1:
                    roots.add(groups.find(nr*cols+nc))
            best = max(best, 1 + sum(groups.size[root] for root in roots))
    return best

assert largest_island([[1, 1], [1, 0]]) == 4
assert largest_island([[1, 0], [0, 1]]) == 3
assert largest_island([[0, 0], [0, 0]]) == 1
assert largest_island([[1, 1], [1, 1]]) == 4

Work and storage: O(RC α(RC)) time and O(RC) space. Each cell has only four possible neighbors; the deduplication set is constant-sized.

When to recognize it: One flip joins neighboring groups. Their roots and sizes summarize everything needed to score that flip.

Check before applying it: Two neighboring squares may belong to the same island. Count each root once. Trying two flips independently would miss their interaction.

Change one rule

We may flip two water squares. Can we take the two largest one-flip scores and add them?

See what changes

No. Scores may overlap, and two adjacent flips can connect components neither would connect alone. The one-local-change summary does not establish independence between two changes.

Connect

Accounts Merge: Reuse grouping, but summarize group size instead of emails.

Swim in Rising Water: Activate cells gradually instead of testing one isolated flip.

Problem reference: Making A Large Island (Hard). The walkthrough and Python solution above are original course material.