Shifting a 2D grid is like rotating all elements forward by one position. Each element moves to the next column, and elements at the end of a row wrap around to the start of the next row. The last element of the grid wraps to position (0, 0).
By simulating this process k times, we can achieve the desired result. For each shift, we copy each element to its new position in a fresh grid.
cur filled with zeros.c to column c + 1 in the same row.(r, n-1) wraps to ((r + 1) % m, 0).cur.class Solution:
def shiftGrid(self, grid: List[List[int]], k: int) -> List[List[int]]:
m, n = len(grid), len(grid[0])
while k:
cur = [[0] * n for _ in range(m)]
for r in range(m):
for c in range(n - 1):
cur[r][c + 1] = grid[r][c]
for r in range(m):
cur[(r + 1) % m][0] = grid[r][n - 1]
grid = cur
k -= 1
return gridWhere is the number of rows in the grid, is the number of columns in the grid, and is the shift count.
Instead of creating a new grid each time, we can shift elements in place. The key insight is that shifting works like a rotation: each element takes the place of the previous one. By keeping track of the last element (which wraps to the first position), we can propagate values through the entire grid in a single pass.
grid[m-1][n-1] as prev.prev.Where is the number of rows in the grid, is the number of columns in the grid, and is the shift count.
A 2D grid can be viewed as a 1D array if we flatten it row by row. Shifting in a 1D array is simply rotating elements to the right. The classic way to rotate an array by k positions is to use three reversals: reverse the entire array, then reverse the first k elements, then reverse the remaining elements.
arr where arr[r * n + c] = grid[r][c].k by taking k % N (where N = m * n) to avoid unnecessary full rotations.k elements.k to N-1.class Solution:
def shiftGrid(self, grid: List[List[int]], k: int) -> List[List[int]]:
m, n = len(grid), len(grid[0])
N = m * n
k %= N
arr = [0] * N
for r in range(m):
for c in range(n):
arr[r * n + c] = grid[r][c]
def reverse(l, r):
while l < r:
arr[l], arr[r] = arr[r], arr[l]
l += 1
r -= 1
reverse(0, N - 1)
reverse(0, k - 1)
reverse(k, N - 1)
for r in range(m):
for c in range(n):
grid[r][c] = arr[r * n + c]
return gridWhere is the number of rows in the grid and is the number of columns in the grid.
Instead of actually shifting elements, we can compute where each element should go after k shifts. The position of an element in a flattened grid is r * n + c. After k shifts, this becomes (r * n + c + k) % (m * n). We can then convert this back to 2D coordinates.
This approach processes each element exactly once, computing its final position directly.
(r, c):newVal = (r * n + c + k) % (m * n).newR = newVal / n, newC = newVal % n.res[newR][newC] = grid[r][c].class Solution:
def shiftGrid(self, grid: List[List[int]], k: int) -> List[List[int]]:
M, N = len(grid), len(grid[0])
def posToVal(r, c):
return r * N + c
def valToPos(v):
return [v // N, v % N]
res = [[0] * N for _ in range(M)]
for r in range(M):
for c in range(N):
newVal = (posToVal(r, c) + k) % (M * N)
newR, newC = valToPos(newVal)
res[newR][newC] = grid[r][c]
return resWhere is the number of rows in the grid and is the number of columns in the grid.