【leetcode】236. 二叉树的最近公共祖先

45 阅读1分钟

leetcode-236.png

  • 如果当前节点是 null,返回 null
  • 如果当前节点是 p 或 q,直接返回当前节点。
  • 递归地在左右子树中寻找 p 和 q
    • 如果在左右子树中分别找到了 p 和 q,说明当前节点就是 LCA。
    • 如果在一棵子树中找到了 p 或 q,返回这个子树中的结果。
    • 如果左右子树都没找到,返回 null

递归

var lowestCommonAncestor = function (root, p, q) {
    if (!root || root === p || root === q) return root
    let left = lowestCommonAncestor(root.left, p, q)
    let right = lowestCommonAncestor(root.right, p, q)
    if (left && right) return root
    return left ? left : right
};

测试用例1:

p = 10, q = 11
即两个都不在树里面,此时left = null,right = null
返回root = null

测试用例2:

p = 5, q = 1
此时left = 5, right = 1
返回root

测试用例3:

p = 5, q = 10(不在树内)
此时left = 5,right = null
返回left

公共路径

var lowestCommonAncestor = function (root, p, q) {
    var findPath = function (node, target, path) {
        if (!node) return false;
        path.push(node);
        if (node === target) return true;
        if (
            findPath(node.left, target, path) ||
            findPath(node.right, target, path)
        )
            return true;
        // 回溯
        path.pop();
        return false;
    };
    const pPath = [],
        qPath = [];
    findPath(root, p, pPath);
    findPath(root, q, qPath);
    let i = 0;
    while (i < pPath.length && i < qPath.length && pPath[i] === qPath[i]) {
        i++;
    }
    return pPath[i - 1];
};