← [ BACK_TO_NOTES ]

打家劫舍 III

树形 DP 入门题:每个节点维护“偷 / 不偷”两种状态,自底向上合并左右子树。

#algorithm #snippet #growing #leetcode #dp

[!info] related notes 动态规划 打家劫舍 二叉树基础 树形 DP

打家劫舍 III

题目链接:https://leetcode.cn/problems/house-robber-iii/

为什么是树形 DP

每个节点都面临两种状态:

  • 偷当前节点
  • 不偷当前节点

并且选择会影响左右孩子是否能偷。

状态设计

对每个节点返回一个长度为 2 的数组:

  • res[0]:在当前节点整棵子树内、不偷当前节点时的最大收益
  • res[1]:在当前节点整棵子树内、偷当前节点时的最大收益

转移

  • 不偷当前节点:左右子树都可以偷也可以不偷,取各自最大值
  • 偷当前节点:左右孩子都不能偷

JavaScript

var rob = function(root) {
    function dfs(node) {
        if (!node) return [0, 0];

        const left = dfs(node.left);
        const right = dfs(node.right);

        const notRob = Math.max(left[0], left[1]) + Math.max(right[0], right[1]);
        const robNode = node.val + left[0] + right[0];

        return [notRob, robNode];
    }

    const res = dfs(root);
    return Math.max(res[0], res[1]);
};

每个节点访问一次,时间 O(n),递归栈 O(h)。退化成链时 h = n,JavaScript 递归实现可能超过调用栈限制;可改用显式栈做后序遍历。

创建于 2026/3/18 更新于 2026/10/7
Digital Biome
Access

键盘导航

j / k / ↑ / ↓
选择对象
Enter / o
打开选择
/ 或 Ctrl+K
全站搜索
i / f / 1–4
筛选当前列表
g → h / l / p / t / a
首页 / 笔记 / 项目 / 工具 / About
r → 1–9
打开所选对象的关联
u
返回上一页
Esc
关闭浮层 / 取消命令;输入框内清空文本