【题目描述】
给定一个二叉树,找出其最小深度。
最小深度是从根节点到最近叶子节点的最短路径上的节点数量。
说明:叶子节点是指没有子节点的节点。
【测试用例】
示例1:
输入:root = [3,9,20,null,null,15,7]
输出:2
示例2:
输入:root = [2,null,3,null,4,null,5,null,6]
输出:5
【思路分析】
在之前我们求过二叉树的最大深度,而这道题求二叉树的最小深度,很多人可能第一时间会想到:求最大深度的时候返回的是左右子树深度大的一个+1,那么求最小深度时返回小的一个+1就可以了。但是有这么简单吗?
题目中“最小深度是从根节点到最近叶子节点的最短路径上的节点数量”,叶子节点直接否定了上述的想法。来看一个例子(图引自力扣题解“代码随想录”):
如果按照上述思想来算最小深度,会发现这棵树的深度为1(因为左子树为空,会返回0+1=1),但是根据题目的描述,这棵树的最小深度为3,所以上述算法是错的。那么正确的应该如何呢?
首先,如果传入递归的节点root为空,那么肯定直接return 0,这是没有疑问的。仔细分析上述例子的情况,我们可以容易的发现一种特殊情况,当一个节点root的左子树为空时,这个节点的深度就等于其右子树的深度+1,同理,当该节点的右子树为空时,这个节点的深度就等于其左子树的深度+1。这时我们考虑完全了吗?没有。还有一种更特殊的情况是,左右子树均为空,即该节点是叶子节点,这时应该return 1(该叶子节点的深度为1)。
至此,特殊情况全部考虑完了。再看一般情况:一般情况就是节点root的左右子树均不为空,那么此时root的深度就是左右子树深度小的一个+1。
【参考代码】
C实现
#include <stdio.h>
//easy-111-二叉树的最小深度
int minDepth(struct TreeNode* root);
struct TreeNode {
int val;
struct TreeNode *left;
struct TreeNode *right;
};
int minDepth(struct TreeNode* root) {
if(NULL == root){
return 0;
}
if(root->left==NULL && root->right==NULL){
return 1;
}
int left = minDepth(root->left);
int right = minDepth(root->right);
if(left == 0){
return right + 1;
}
if(right == 0){
return left + 1;
}
return left < right ? left + 1 : right + 1;
}
C++实现
#include <iostream>
using namespace std;
//easy-111-二叉树的最小深度
struct TreeNode {
int val;
TreeNode *left;
TreeNode *right;
TreeNode() : val(0), left(nullptr), right(nullptr) {}
TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {}
};
class Solution {
public:
int minDepth(TreeNode* root);
};
int Solution::minDepth(TreeNode* root){
if(NULL == root){
return 0;
}
if(root->left==NULL && root->right==NULL){
return 1;
}
int left = minDepth(root->left);
int right = minDepth(root->right);
if(left == 0){
return right + 1;
}
if(right == 0){
return left + 1;
}
return 1 + min(left, right);
}