第169场周赛实录(深度遍历/广度遍历(bfs/dfs))

1306. 跳跃游戏 III

难度:中等

这里有一个非负整数数组 arr,你最开始位于该数组的起始下标 start 处。当你位于下标 i 处时,你可以跳到 i + arr[i] 或者 i - arr[i]。

请你判断自己是否能够跳到对应元素值为 0 的 任意 下标处。

注意,不管是什么情况下,你都无法跳到数组之外。

示例 1:

输入:arr = [4,2,3,0,3,1,2], start = 5
输出:true
解释:
到达值为 0 的下标 3 有以下可能方案:
下标 5 -> 下标 4 -> 下标 1 -> 下标 3
下标 5 -> 下标 6 -> 下标 4 -> 下标 1 -> 下标 3

示例 2:

输入:arr = [4,2,3,0,3,1,2], start = 0
输出:true
解释:
到达值为 0 的下标 3 有以下可能方案:
下标 0 -> 下标 4 -> 下标 1 -> 下标 3

示例 3:

输入:arr = [3,0,2,1,2], start = 2
输出:false
解释:无法到达值为 0 的下标 1 处。

提示:

  • 1 <= arr.length <= 5 * 10^4
  • 0 <= arr[i] < arr.length
  • 0 <= start < arr.length

解决方案 :

深度遍历关键在于标记,意思是当向树深度遍历时,要记得对遍历的位置进行标记防止反复遍历,当遍历不下去时还需要记得删除该标记,防止其他数分支访问不到该节点,若无节点可访问时,则返回false;若访问到的节点符合条件时,则返回True。

class Solution:
    def dfs(self, arr, start, mark):
        print(start, arr[start])
        if arr[start] == 0:
            return True
        mark[start] += 1
        if 0 <= start - arr[start] < len(arr) and mark[start - arr[start]] == 0:
            if self.dfs(arr, start - arr[start], mark):
                return True
        if 0 <= start + arr[start] < len(arr) and mark[start + arr[start]] == 0:
            if self.dfs(arr, start + arr[start], mark):
                return True
        mark[start] -= 1
        return False
    
    def canReach(self, arr: List[int], start: int) -> bool:
        return self.dfs(arr, start, [0 for _ in range(len(arr))])

广度遍历与深度遍历不同的是,除了要标记访问的节点外,广度遍历重点是首先要设定一个数组,作为广度遍历的源头,且每次遍历这个数组以广度进行遍历并更新这个数组,如果这个数组没值时,则返回False

以下是网上某大神写的广度遍历:

class Solution:
    def canReach(self, arr: List[int], start: int) -> bool:
        q, v, n = [start], {start}, len(arr)
        while q:
            p = []
            for i in q:
                if not arr[i]:
                    return True
                for j in i - arr[i], i + arr[i]:
                    if 0 <= j < n and j not in v:
                        p.append(j)
                        v.add(j)
            q = p
        return False

顺带附上该大神的深度遍历,很便捷。

class Solution:
    def canReach(self, arr: List[int], start: int) -> bool:
        n, v = len(arr), set()
        def f(i):
            if not arr[i]:
                return True
            elif i not in v:
                v.add(i)
                return 0 <= i - arr[i] < n and f(i - arr[i]) or 0 <= i + arr[i] < n and f(i + arr[i])
        return f(start)
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章