LeetCode刷题笔记 124

题目:二叉树中的最大路径和

给定一个非空二叉树,返回其最大路径和。

本题中,路径被定义为一条从树中任意节点出发,达到任意节点的序列。该路径至少包含一个节点,且不一定经过根节点。

示例 1:
输入: [1,2,3]

       1
      / \
     2   3

输出: 6
示例 2:
输入: [-10,9,20,null,null,15,7]

	   -10
	   / \
	  9  20
	    /  \
	   15   7

输出: 42

答案:
首先需要明确,路径是不允许走回头路的,例如示例2中,9->-10->20->15->7不是一条路径

解题思路:
参考链接:https://leetcode-cn.com/problems/binary-tree-maximum-path-sum/solution/er-cha-shu-zhong-de-zui-da-lu-jing-he-by-ikaruga/

对每个抽象出来的二叉树 abc,a 是根结点(递归中的 root),bc 是左右子结点(代表其递归后的最优解)。
最大的路径,可能的路径情况:

    a          
   / \
  b   c

1.b + a + c。
2.b + a + a 的父结点。
3.c + a + a 的父结点。
注:再重申一次,这里的a、b、c是抽象的当前递归根节点,当前左子树(具体的左子树的子树都已经在之前的递归计算过了,已经抽象综合到本左子树里),当前右子树(也是抽象的)

其中情况 1,表示如果不联络父结点的情况,或本身是根结点的情况。
这种情况是没法递归的,但是结果有可能是全局最大路径和。
情况 2 和 3,递归时计算 a+b 和 a+c,选择一个更优的方案返回,也就是上面说的递归后的最优解。

再解释地具体一点:

  -10
  / \
 9  20        20              a     可以选择15--20--7作为路径              -10(a)
   /  \      /  \  可以抽象为 / \    也可以选择-10--20--15作为路径  再递归   /  \     时,c表示20(根节点的值)+15(左子树和右子树产生的值较大的一个)
  15   7    15   7          b   c   也可以选择-10--20--7作为路径     左子树(b)   右子树(c)

所要做的就是递归,递归时记录好全局最大和,返回联络最大和。

class Solution {
    public int maxPathSum(TreeNode root) {
		int[] maxSum = new int[1];   //使用数组而非int型变量是因为可以将地址传递进去然后直接更改数据(相当于全局变量)
		maxSum[0] = Integer.MIN_VALUE;//初始化为最小值。
		maxPathSumHelper(root, maxSum);
		return maxSum[0];
	}

	public int maxPathSumHelper(TreeNode root, int[] maxSum) {
		if (root == null) {
			return 0;
		}
		int lSum = Math.max(maxPathSumHelper(root.left, maxSum),0); //lSum<0 则赋为0
		int rSum = Math.max(maxPathSumHelper(root.right, maxSum),0);//rSum<0 则赋为0
		maxSum[0] = Math.max(root.val + lSum + rSum, maxSum[0]);//每次都求一下当前结点与左子树和右子树的最大值,更新全局最大和
		return root.val + Math.max(rSum, lSum); //选择左子树和右子树产生的值较大的一个
	}
}

你可能感兴趣的:(LeetCode,二叉树,leetcode,java)