题目链接:104. 二叉树的最大深度
题目描述
给定一个二叉树 root
,返回其最大深度。
二叉树的 最大深度 是指从根节点到最远叶子节点的最长路径上的节点数。
示例 1:
输入:root = [3,9,20,null,null,15,7] 输出:3
示例 2:
输入:root = [1,null,2] 输出:2
提示:
- 树中节点的数量在
[0, 104]
区间内。 -100 <= Node.val <= 100
文章讲解:代码随想录
视频讲解:二叉树的高度和深度有啥区别?究竟用什么遍历顺序?很多录友搞不懂 | LeetCode:104.二叉树的最大深度_哔哩哔哩_bilibili
题解1:后续遍历
首先先理解二叉树的深度和高度:
- 二叉树节点的深度:指从根节点到该节点的最长简单路径边的条数或者节点数(取决于深度从0开始还是从1开始)。
- 二叉树节点的高度:指从该节点到叶子节点的最长简单路径边的条数或者节点数(取决于高度从0开始还是从1开始)。
根节点的高度就是二叉树的最大深度。
思路:使用后序遍历,先遍历左子树找出左孩子的最大高度,再遍历右子树找出右孩子的最大高度,最后比较将大的一方加1,即为整个二叉树的最大深度。
递归分析:
- 确定递归函数的参数和返回值:参数为二叉树的节点,返回值为当前节点的高度。
- 确定递归终止条件:当前节点为空节点时,返回高度0。
- 确定单层递归逻辑:先求左孩子的高度,再求右孩子的高度,取大的一方加上1为当前节点的高度,并返回。
/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/
/**
* @param {TreeNode} root
* @return {number}
*/
var maxDepth = function(root) {
if (!root) {
return 0;
}
return Math.max(maxDepth(root.left), maxDepth(root.right)) + 1;
};
分析:时间复杂度为 O(n),空间复杂度为 O(logn)。
题解2:前序遍历
思路:使用前序遍历,求出每个叶子节点的深度,其中最大的深度即为二叉树的最大深度。
/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/
/**
* @param {TreeNode} root
* @return {number}
*/
var maxDepth = function(root) {
let res = 0;
if (!root) {
return 0;
}
const preorder = function (node, depth) {
res = depth > res ? depth : res; // 中
node.left && preorder(node.left, depth + 1); // 左
node.right && preorder(node.right, depth + 1); // 右
};
preorder(root, 1); // 根节点的深度为1
return res;
};
分析:时间复杂度为 O(n),空间复杂度为 O(logn)。
题解3:层序遍历
思路:使用层序遍历,记录二叉树的层数,二叉树的层数即为二叉树的最大深度。
/**
* Definition for a binary tree node.
* function TreeNode(val, left, right) {
* this.val = (val===undefined ? 0 : val)
* this.left = (left===undefined ? null : left)
* this.right = (right===undefined ? null : right)
* }
*/
/**
* @param {TreeNode} root
* @return {number}
*/
var maxDepth = function(root) {
const queue = [];
if (root) {
queue.push(root);
}
let deep = 0;
while (queue.length > 0) {
let size = queue.length;
while (size--) {
const node = queue.shift();
node.left && queue.push(node.left);
node.right && queue.push(node.right);
}
deep++;
}
return deep;
};
分析:时间复杂度为 O(n),空间复杂度为 O(n)。
类似题 559. N 叉树的最大深度
题目链接:559. N 叉树的最大深度
思路:和求二叉树的最大深度类似,可以使用后续遍历求根节点的高度即为 N 叉树的最大深度,或者用前序遍历和层序遍历直接求 N 叉树的最大深度。
后序遍历
/**
* // Definition for a Node.
* function Node(val,children) {
* this.val = val;
* this.children = children;
* };
*/
/**
* @param {Node|null} root
* @return {number}
*/
var maxDepth = function(root) {
if (!root) {
return 0;
}
if (root.children.length === 0) {
return 1;
}
return Math.max(...root.children.reduce((pre, node) => pre.push(maxDepth(node)) && pre, [])) + 1;
};
前序遍历
/**
* // Definition for a Node.
* function Node(val,children) {
* this.val = val;
* this.children = children;
* };
*/
/**
* @param {Node|null} root
* @return {number}
*/
var maxDepth = function(root) {
if (!root) {
return 0;
}
let res = 0;
const preorder = function (node, depth) {
res = depth > res ? depth : res;
node.children.forEach(node => preorder(node, depth + 1));
}
preorder(root, 1);
return res;
};
层序遍历
/**
* // Definition for a Node.
* function Node(val,children) {
* this.val = val;
* this.children = children;
* };
*/
/**
* @param {Node|null} root
* @return {number}
*/
var maxDepth = function(root) {
let depth = 0;
const queue = [];
if (root) {
queue.push(root);
}
while (queue.length > 0) {
depth++;
let size = queue.length;
while (size--) {
const node = queue.shift();
node.children.forEach(node => queue.push(node));
}
}
return depth;
};
分析:时间复杂度为 O(n),空间复杂度为 O(logn)。
收获
学会了通过二叉树的多种遍历方式来求二叉树的最大深度,同时也学会了从二叉树拓展到 N 叉树。