2617. 网格图中最少访问的格子数

2023/04/12 leetcode 共 1305 字,约 4 分钟

title

problem link

给你一个下标从 0 开始的 m x n 整数矩阵 grid 。你一开始的位置在 左上角 格子 (0, 0) 。

当你在格子 (i, j) 的时候,你可以移动到以下格子之一:

  • 满足 j < k <= grid[i][j] + j 的格子 (i, k) (向右移动),或者
  • 满足 i < k <= grid[i][j] + i 的格子 (k, j) (向下移动)。

请你返回到达 右下角 格子 (m - 1, n - 1) 需要经过的最少移动格子数,如果无法到达右下角格子,请你返回 -1 。

示例 1:

img

输入:grid = [[3,4,2,1],[4,2,3,1],[2,1,0,0],[2,4,0,0]]
输出:4
解释:上图展示了到达右下角格子经过的 4 个格子。

示例 2:

img

输入:grid = [[3,4,2,1],[4,2,1,1],[2,1,1,0],[3,4,1,0]]
输出:3
解释:上图展示了到达右下角格子经过的 3 个格子。

示例 3:

img

输入:grid = [[2,1,0],[1,0,0]]
输出:-1
解释:无法到达右下角格子。

提示:

  • m == grid.length
  • n == grid[i].length
  • 1 <= m, n <= 105
  • 1 <= m * n <= 105
  • 0 <= grid[i][j] < m * n
  • grid[m - 1][n - 1] == 0

solution

在线BFS.

每行每列都是个sortedlist。

解法2, 用堆也行,如果是堆,堆顶已经删了,就不停pop。参考

class Solution:
    def minimumVisitedCells(self, grid: List[List[int]]) -> int:
        import sortedcontainers
        m, n = len(grid), len(grid[0])
        rs = [sortedcontainers.SortedList(range(n)) for _ in range(m)]
        cs = [sortedcontainers.SortedList(range(m)) for _ in range(n)]
        q = collections.deque()
        q.append((0, 0))
        steps = 0
        ans = {}
        while q:
            steps += 1
            for _ in range(len(q)):
                i, j = q.popleft()
                ans[(i, j)] = steps
                v = grid[i][j]
                # 竖着走
                l = cs[j].bisect_left(i + 1)
                r = cs[j].bisect_right(i + v)
                for k in range(r - 1, l - 1, -1):
                    q.append((cs[j][k], j))
                    # row也需要同步更新
                    rs[cs[j][k]].discard(j)
                    del cs[j][k]
                # 横着走
                l = rs[i].bisect_left(j + 1)
                r = rs[i].bisect_right(j + v)
                for k in range(r - 1, l - 1, -1):
                    q.append((i, rs[i][k]))
                    cs[rs[i][k]].discard(i)
                    del rs[i][k]
                # print(steps, i,j, v, rs[i], cs[j], ans)
        # print(ans)
        return ans.get((m - 1, n - 1), -1)


Search

    Table of Contents