# Replace for loops with iterables and .map

Yesterday I participated in a weekly leetcode contest and came across this question:

Here’s the straight forward iterative solution:

``````const largestLocalIterative = (grid) => {
const res = [...Array(grid.length - 2)].map((_) =>
Array(grid.length - 2).fill(0)
);
for (let row = 0; row < grid.length - 2; row++)
for (let col = 0; col < grid.length - 2; col++)
for (let i = row; i < row + 3; i++)
for (let j = col; j < col + 3; j++)
res[row][col] = Math.max(res[row][col], grid[i][j]);
return res;
};
``````

However, we can spice it up with a functional spin:

``````function* range(start, end) {
for (let i = start; i < end; i++) yield i;
}

const largestLocal = (grid) =>
[...range(0, grid.length - 2)].map((row) =>
[...range(0, grid.length - 2)].map((col) =>
Math.max(
...grid
.slice(row, row + 3)
.flatMap((rowObj) => rowObj.slice(col, col + 3))
)
)
);
``````

Here’s are some breakdowns:

The Outer loop iterates over each cell in the `maxLocal` grid.

The iterative approach

``````for (let row = 0; row < grid.length - 2; row++)
for (let col = 0; col < grid.length - 2; col++)
``````

is equivalent to

``````[...range(0, grid.length - 2)].map((row) =>
[...range(0, grid.length - 2)].map((col) =>
)
);
``````

The Inner loops fills the current cell’s value in the `maxLocal` grid.

The iterative approach

``````for (let i = row; i < row + 3; i++)
for (let j = col; j < col + 3; j++)
res[row][col] = Math.max(res[row][col], grid[i][j]);
``````

is equivalent to

``````Math.max(
...grid
.slice(row, row + 3)
.flatMap((rowObj) => rowObj.slice(col, col + 3))
)
``````

Note the cute `range` generator I wrote. It is similar to python’s `range`. However, I decided to use Javascript instead of Python because of the built in `.map` and `.flatMap` on the native array object.

I can even define an generator directly on the native Number object.

``````Number.prototype[Symbol.iterator] = function* () {
for (var i = 0; i < this; i++) yield i;
};
``````

This allows me to drop the `range` function in certain situations. For example, I can do `[...(grid.length - 2)]` instead of `[...range(0, grid.length - 2)]`.

Update 8/24/2022:

I realized that I can write a cleaner solution in python since it has `list comprehension`:

``````def largestLocal(self, grid: List[List[int]]) -> List[List[int]]:
R, C = len(grid) - 2, len(grid) - 2
return [[max(max(row[c: c + 3]) for row in grid[r: r + 3])
for c in range(C)] for r in range(R)]
``````