leetcode 124

leetcode 124 二叉树中的最大路径和@TOC

解题思路:动态规划

每一条路径,一定是先上升0 ~ n个节点,到达顶点,然后下降0 ~ n个顶点。换言之,每一个节点都可以作为顶点,并有一条最佳路径。

有一个类似的题目,求数组的最长子数组。dp[i]表示以nums[i]为结尾时的最大子数组和。

针对二叉树的最大路径和,可以用dp[I]表示以I为顶点时的最大路径和。

因此为求得最大路径和,就需要遍历每一个节点,求每一个dp[I]。联想到的第一个就是递归。递归函数可以表示以root为顶点结尾时的最大路径,返回值代表root作为子节点时的最长路径。

class Solution {
private:
    int MAXSUM = INT_MIN;
public:
    int maxSum(TreeNode* root) {        //maxSum以root为根节点结尾时的最大路径,返回值是root作为子节点时的最长路径 
        if (root == NULL)   return 0;
        int leftSum = max(maxSum(root->left), 0);
        int rightSum = max(maxSum(root->right), 0);
        int nowSum = leftSum + rightSum + root->val;
        MAXSUM = max(MAXSUM, nowSum);
        return max(leftSum, rightSum) + root->val;      //
    }
    int maxPathSum(TreeNode* root) {
        maxSum(root);
        return MAXSUM;
    }
}    

参考leetcode评论区的一个大佬的思路:

这题目的难点在于理解题意和转化题意。
我们可以结合 数组的最大子数组和 的思路去解题。

  1. 「可以从任意节点出发, 到达任意节点」 的路径,
    一定是先上升( 0 ~ n 个)节点, 到达顶点, 后下降( 0 ~ n 个)节点。
    我们可以通过枚举顶点的方式来枚举路径。

  2. 我们枚举顶点时, 可以把路径分拆成3部分: 左侧路径、右侧路径和顶点。
    如下面的路径, 顶点为 20, 左侧路径为 6 -> 15, 右侧为 6 -> 7。

    -10
    /
    9 [20]
    /
    [15] [7]
    / /
    [6] 4 [6]

    以当前节点为顶点的路径中, 最大和为 两侧路径的最大和 + 节点的值。
    需要注意的是, 两侧路径也可能不选, 此时取 0。

  3. 如何求两侧路径最大和? 看一个类似问题:求数组的最大子数组和。
    动态规划: dp[i] 代表以 nums[i] 为结尾的子数组的最大和。
    转移方程: dp[i] = max(dp[i-1], 0) + nums[i]。

  4. 在树上, 设 dp[C] 代表以当前节点为结尾的最大上升路径和,
    则我们需要对节点的左右子树做一个选择, 有
    dp[C] = max(max(dp[L], 0), max(dp[R], 0)) + C.val
    式中, C,L,R 分别代指 当前节点、左子节点、右子节点。

  5. 最后, 以当前节点为顶点的路径中, 最大的和为
    max(dp[L], 0) + max(dp[R], 0) + C.val。
    我们枚举顶点, 并记录最大答案。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值