【每日算法0301】搜索与回溯算法(中等)

66 阅读2分钟

开启掘金成长之旅!这是我参与「掘金日新计划 · 2 月更文挑战」的第 21天,点击查看活动详情

题目

剑指 Offer 55 - I. 二叉树的深度

输入一棵二叉树的根节点,求该树的深度。从根节点到叶节点依次经过的节点(含根、叶节点)形成树的一条路径,最长路径的长度为树的深度。

示例:

给定二叉树 [3,9,20,null,null,15,7]

    3
   / \
  9  20
    /  \
   15   7

返回它的最大深度 3 。

分析

做深度搜索迭代,每次遍历玩一个方向记录层数,比较记录最大值

迭代方法实现

  • 确定入参

传入节点和当前的层数,节点用于向下搜索,层数用于累积得到某个方向的层数

  • 确定退出条件

节点为空时退出迭代,并且对比更新最大值

  • 确定迭代逻辑

节点存在,层数 + 1

分别向左右节点进行迭代

最后返回结果

实现

function maxDepth(root: TreeNode | null): number {
    let max = 0
    function dfs (node, count) {
        if (!node) {
            max = max < count ? count : max
            return
        }
        count ++
        dfs(node.left, count)
        dfs(node.right, count)
    }
    dfs(root, 0)
​
    return max
};

补充

做了下一道题后,优化一下实现

function maxDepth(root: TreeNode | null): number {
    if (!root) return 0
​
    return 1 + Math.max(maxDepth(root.left), maxDepth(root.right))
};

题目

剑指 Offer 55 - II. 平衡二叉树

输入一棵二叉树的根节点,判断该树是不是平衡二叉树。如果某二叉树中任意节点的左右子树的深度相差不超过1,那么它就是一棵平衡二叉树。

示例:

给定二叉树 [3,9,20,null,null,15,7]

    3
   / \
  9  20
    /  \
   15   7

分析

使用递归的方法,自顶向下递归

树满足平衡二叉树条件,需要判断

  • 当前节点是否满足差值小于2
  • 它的子节点必须同样满足上一条件

设计迭代方法

  • 退出条件

当节点不存在时,反回0

  • 迭代逻辑

需要计算出当前方向下的最大值

即每一层取 1 + Max(左节点取最大路径, 右节点取最大路径)

迭代求出左右最大值

  • 比较左右最大值的差值,并做下一层左右节点的判断

实现

function isBalanced(root: TreeNode | null): boolean {
​
    if (!root) return true
​
    function getMax(node) {
        if (!node) return 0
​
        return 1 + Math.max(getMax(node.left), getMax(node.right))
    }
    let left = getMax(root.left)
    let right = getMax(root.right)
​
    return Math.abs(left - right) < 2 && isBalanced(root.left) && isBalanced(root.right)
};