代码随想录二刷 | 二叉树 |513.找树左下角的值
题目描述
给定一个二叉树的根节点 root,请找出该二叉树的最底层最左边节点的值。
假设二叉树中至少有一个节点。
示例 1:
输入: root = [2,1,3]
输出: 1
示例 2:
输入: [1,2,3,4,null,5,6,null,null,7]
输出: 7
提示:
- 二叉树的节点个数的范围是 [1,104]
- -231 <= Node.val <= 231 - 1
解题思路
本题要找出树的最后一行的最左边的值。用层序遍历是非常简单的,反而用递归的话会比较难一点。
递归法
我们要找的是最后一行的最左边的值,因此,起始我们找的是最大深度的最左边的值。
可以使用前序遍历(当然中序,后序都可以,因为本题没有 中间节点的处理逻辑,只要左优先就行),保证优先左边搜索,然后记录深度最大的叶子节点,此时就是树的最后一行最左边的值。
递归三部曲
-
确定递归函数的参数和返回值
参数必须有要遍历的树的根节点,还有就是一个int型的变量用来记录最长深度。 这里就不需要返回值了,所以递归函数的返回类型为void。
本题还需要类里的两个全局变量,maxLen用来记录最大深度,result记录最大深度最左节点的数值。cppint maxDepth = INT_MIN; // 全局变量,记录最大深度 int result; // 全局变量 最大深度最左节点的数值 void traversal(TreeNode* root, int depth)
-
确定递归的终止条件
当遇到叶子节点的时候,就需要统计一下最大的深度了,所以需要遇到叶子节点来更新最大深度。cppif (root->left == NULL && root->right == NULL) { if (depth > maxDepth) { maxDepth = depth; // 更新最大深度 result = root->val; // 最大深度最左面的数值 } }
-
确定单层递归的逻辑
在找最大深度的时候,递归的过程中依然要使用回溯,代码如下:cppif (root->left) { depth++; // 深度+1 traversal(root->left, depth); depth--; // 回溯,深度-1 } if (root->right) { depth++; // 深度 + 1 traversal(root->right, depth); depth--; // 回溯,深度-1 }
迭代法
迭代法只需要记录最后一行第一个节点的数值就可以了。
代码实现
递归法
cpp
class Solution {
public:
int maxDepth = INT_MIN;
int result;
void traversal(TreeNode* root, int depth) {
if (root->left == NULL && root->right == NULL) {
if (depth > maxDepth) {
maxDepth = depth;
result = root->val;
}
return;
}
if (root->left) {
depth++; // 深度+1
traversal(root->left, depth);
depth--; // 回溯,深度-1
}
if (root->right) {
depth++; // 深度 + 1
traversal(root->right, depth);
depth--; // 回溯,深度-1
}
}
int findBottomLeftValue(TreeNode* root) {
traversal(root, 0);
return result;
}
};
迭代法
cpp
class Solution {
public:
int findBottomLeftValue(TreeNode* root) {
queue<TreeNode*> que;
if (root != NULL) que.push(root);
int result = 0;
while (!que.empty()) {
int size = que.size();
for (int i = 0; i < size; i++) {
TreeNode* node = que.front();
que.pop();
if (i == 0) result = ndoe->val;
if (node->left) que.push(node->left);
if (node->right) que.push(node->right);
}
}
return result;
}
};