设想有个机器人坐在一个网格的左上角,网格 r 行 c 列。机器人只能向下或向右移动,但不能走到一些被禁止的网格(有障碍物)。设计一种算法,寻找机器人从左上角移动到右下角的路径。
网格中的障碍物和空位置分别用 1 和 0 来表示。
返回一条可行的路径,路径由经过的网格的行号和列号组成。左上角为 0 行 0 列。如果没有可行的路径,返回空数组。
示例:
输入:
[
[0,0,0],
[0,1,0],
[0,0,0]
]
输出: [[0,0],[0,1],[0,2],[1,2],[2,2]]
解释:
输入中标粗的位置即为输出表示的路径,即
0行0列(左上角) -> 0行1列 -> 0行2列 -> 1行2列 -> 2行2列(右下角)
分析: 深度优先搜索问题,从左上角到右下角,只需要找到一条可行路径即可,因此在找到符合条件的路径后即可返回不再查找, 通过return True 或者False判断是否还需要继续查找,注意此题刚开始没有添加mark数组用来标识已经走过的路径,导致最终超时,对于同一个位置(i, j),有着不同的走法可以到达这个点,而经过这个点的后续路径无法达到右下角时,就会产生重复无效的递归查找,因此,此题也需要通过添加标识进行判断。
class Solution:
def pathWithObstacles(self, obstacleGrid: List[List[int]]) -> List[List[int]]:
path = []
row = len(obstacleGrid)
col = len(obstacleGrid[0])
mark = [[0 for i in range(col)] for j in range(row)]
def DFS(i, j):
if i == row or j == col or obstacleGrid[i][j] == 1 or mark[i][j] == 1:
return False
if i == row-1 and j == col - 1 and obstacleGrid[i][j] == 0:
path.append([i, j])
return True
mark[i][j] = 1
path.append([i, j])
if DFS(i, j+1):
return True
if DFS(i+1, j):
return True
path.pop()
return False
DFS(0, 0)
return path