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

二叉树最近公共祖先
整体思路:计算p,q两节点的最近公共祖先,可以分为以下几步

  1. 寻找p,q节点的祖先,更新p,q节点。使得它们处于树的同一层
  2. 以新的p,q节点为基准。p,q节点同时向父节点跳跃。当p == q时,表明找到最近公共祖先

由上述思路可知,我们需要维护以下数据

  • 所有节点的父节点
  • 所有节点的深度
/**
 * Definition for a binary tree node.
 * public class TreeNode {
 *     int val;
 *     TreeNode left;
 *     TreeNode right;
 *     TreeNode(int x) { val = x; }
 * }
 */
class Solution {
    // 维护每个节点的父亲节点
    public Map<TreeNode, TreeNode> parent = new HashMap<>();

    // 维护每个节点的深度
    public Map<TreeNode, Integer> height = new HashMap<>();

    public TreeNode lowestCommonAncestor(TreeNode root, TreeNode p, TreeNode q) {
        // 初始化parent, height
        dfs(root, null, 0); 
        // 节点跳至同一层级
        while (height.get(p) > height.get(q)) {
            // 跳跃p节点
            p = parent.get(p);
        }
        // 如果p == q, 表示节点已经跳至公共祖先
        if (p == q) return p;

        // 节点跳至同一层级
        while (height.get(p) < height.get(q)) {
            // 跳跃q节点
            q = parent.get(q);
        }
        // 返回公共节点
        while(p != q) {
            p = parent.get(p);
            q = parent.get(q);
        }
        return p;
    }

    public void dfs(TreeNode cur, TreeNode pre, int h) {
        if (cur == null) return;
        // 记录父亲节点
        parent.put(cur, pre);
        // 记录当前节点的深度
        height.put(cur, h);
        dfs(cur.left, cur, h + 1);
        dfs(cur.right, cur, h + 1);
    }
}

你可能感兴趣的:(1024程序员节)