【前端er每日算法】二叉树深度题目104最大深度/111最小深度

86 阅读2分钟

104. 二叉树的最大深度

给定一个二叉树,找出其最大深度。

二叉树的深度为根节点到最远叶子节点的最长路径上的节点数。

说明: 叶子节点是指没有子节点的节点。

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

    3
   / \
  9  20
    /  \
   15   7
返回它的最大深度 3 

思路

这个直接递归,求深度要用前序遍历,但这里求的是最大深度,则最大深度等于根节点的高度,则可以用后序遍历求根节点的高度来实现。

var maxDepth = function(root) {
    if (!root) {
        return 0;
    }
    const leftDepth = maxDepth(root.left);
    const rightDepth = maxDepth(root.right);
    return 1 + Math.max(leftDepth, rightDepth);
}

好了,上面是最大深度,接下来再求最小深度,也许想当然的在上面的基础上把max换成min?但是却有坑,所有我们继续往下看。

111. 二叉树的最小深度

给定一个二叉树,找出其最小深度。

最小深度是从根节点到最近叶子节点的最短路径上的节点数量。

说明:叶子节点是指没有子节点的节点。

示例 1:

输入:root = [3,9,20,null,null,15,7]

输出:2

思路

这里的一个问题是,如果左右子树有一个为空,则要求非空的子树的最小深度,然后+1返回。所以这个跟求最大深度是不一样的,要注意哦。

var minDepth = function(root) {
    const getDepth = root => {
        if (!root) {
            return 0;
        }
        const leftDepth = getDepth(root.left);
        const rightDepth = getDepth(root.right);
        if (root.left && root.right) {
            return 1 + Math.min(leftDepth, rightDepth);
        } else if (root.left) {
            return 1 + leftDepth;
        } else {
            return 1 + rightDepth;
        }
    }
    return getDepth(root);
};

还有一种使用层次遍历的迭代解法,思路是遇到第一个叶子节点就返回当前的深度,就是这棵树的最小深度。

var minDepth = function(root) {
    if (!root) {
        return 0;
    }
    let depth = 0;
    const queue = [root];
    while (queue.length) {
        const size = queue.length;
        depth++;
        for (let i = 0; i < size; i++) {
            const node = queue.shift();
            if (!node.left && !node.right) {
                return depth;
            }
            if (node.left) {
                queue.push(node.left);
            }
            if (node.right) {
                queue.push(node.right);
            }
        }
    }
    return depth;
}

222. 完全二叉树的节点个数

思路

如果不考虑完全二叉树,则可以用递归求出来左右子树的节点个数,然后相加,再➕1,

如果考虑完全二叉树特性,则判断子树是否是完全二叉树,有的话,根据2的深度次方 -1来求完全二叉树的个数,可以减少时间复杂度。如果不是的话,则按照上面的解法来求解。

 /**
 * @param {TreeNode} root
 * @return {number}
 */
var countNodes = function(root) {
     if (!root) {
        return 0;
    }
    const leftCount = countNodes(root.left);
    const rightCount = countNodes(root.right);
    return leftCount + rightCount + 1;
};

var countNodes = function(root) {
    if (!root) {
        return 0;
    }
    let leftDepth = 0;
    let rightDepth = 0;
    let node = root.left;
    while (node) {
        leftDepth++;
        node = node.left;
    }
    node = root.right;
    while (node) {
        rightDepth++;
        node = node.right;
    }
    if (leftDepth === rightDepth) {
        return Math.pow(2, leftDepth + 1) - 1;
    }
    const leftCount = countNodes(root.left);
    const rightCount = countNodes(root.right);
    return leftCount + rightCount + 1;
};