打劫三部曲-III

5 篇文章 0 订阅
4 篇文章 0 订阅

我们在前两集(第一集,第二集)中通过使用动态规划顺利的通过了挑战,享受了零元大抢购和无限量自助。现在我们要挑战最高难度的富豪区。富豪区的安保果然不同凡响,采用的二叉树的结构,当年Homebrew的作者Max Howell挑战Google就是被二叉树打败。那鸡汤文不是常说XX之下没有一片雪花是无辜的,富豪区居民作为底层制度的设计者需要为整个事件负责。打劫只是手段,目标是要建立一个更公平的制度。

https://www.lintcode.com/problem/house-robber-iii/

遇到二叉树,凭本能就意识到这个问题应该使用递归。问题的本质和之前还是一样,这个节点是抢还是不抢。所以我们每次递归返回的是当前节点作为根节点能获得的最大收益:1)包含该节点;2)不包含该节点。

实现代码如下:

# Python
class Solution:
    # @param {TreeNode} root, the root of binary tree.
    # @return {int} The maximum amount of money you can rob tonight
    def houseRobber3(self, root):
        # write your code here
        return max(self._houseRobber3(root))

    def _houseRobber3(self, root):
        if not root:
            return (0, 0)
        rob_left = self._houseRobber3(root.left)
        rob_right = self._houseRobber3(root.right)
        not_rob = rob_left[1] + rob_right[1] + root.val
        rob = max(rob_left) + max(rob_right)
        return (not_rob, rob)
// Java
public class Solution {
    /**
     * @param root: The root of binary tree.
     * @return: The maximum amount of money you can rob tonight
     */
    public int houseRobber3(TreeNode root) {
        // write your code here
        // 递归,但是每次要返回两个结果,一个包含该节点的,一个不包含该节点的。
        int[] ret = _houseRobber3(root);
        return Math.max(ret[0], ret[1]); // [包含,不包含]
    }
    
    protected int[] _houseRobber3(TreeNode node) {
        int[] ret = new int[]{0, 0};
        if (node != null) {
            int[] rl = _houseRobber3(node.left);
            int[] rr = _houseRobber3(node.right);
            ret[0] = rl[1] + rr[1] + node.val;
            ret[1] = Math.max(rl[0], rl[1]) + Math.max(rr[0], rr[1]);
        }
        return ret;
    }
}

OK,愉快的在富豪区均贫富,三部曲顺利收工。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值