Link:
题目要求
给你一个有根节点root的二叉树,返回它 最深的叶节点的最近公共祖先 。回想一下:
- 叶节点 是二叉树中没有子节点的节点
- 树的根节点的 深度 为
0,如果某一节点的深度为d,那它的子节点的深度就是d+1
- 如果我们假定
A是一组节点S的 最近公共祖先,S中的每个节点都在以A为根节点的子树中,且A的深度达到此条件下可能的最大值。
核心算法和原理
- LCA问题,类似236.二叉树的最近公共祖先,找「LCA候选节点」
- 这次需要找到最深节点的LCA,那么可以在返回值多记录一个「最深节点深度」
- 遍历时,为null返回null,否则dfs左右子树
- 如果dfs结果都不为null则检查左右子树的深度,相等则返回(node, 左右子树的深度) ,否则返回深度较大的那边的dfs结果
- 其余情况看代码,一目了然
代码
/** * Definition for a binary tree node. * 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: typedef pair<TreeNode*, int> pit; TreeNode* lcaDeepestLeaves(TreeNode* root) { auto dfs = [&](this auto&& dfs, TreeNode* node, int depth) -> pit { if (node == nullptr) { return make_pair(nullptr, depth); } pit l = dfs(node->left, depth + 1); pit r = dfs(node->right, depth + 1); if (l.first && r.first) { if (l.second > r.second) { return l; } else if (l.second < r.second) { return r; } else { // 两边子树高度深度相同,说明node就是「以node为根的树中符合要求 // 的LCA」 return make_pair(node, l.second); } } else if (l.first) { return l; } else if (r.first) { return r; } else { // 都为nullptr:说明node是叶子节点,返回node即可 return make_pair(node, depth); } }; return dfs(root, 0).first; } };
