题目:
给定一个二叉树的根节点 root ,和一个整数 targetSum ,求该二叉树里节点值之和等于 targetSum 的 路径 的数目。
路径 不需要从根节点开始,也不需要在叶子节点结束,但是路径方向必须是向下的(只能从父节点到子节点)。
思路: 双重递归 思路:首先先序递归遍历每个节点,再以每个节点作为起始点递归寻找满足条件的路径
class Solution {
int count = 0;
public int pathSum(TreeNode root, int targetSum) {
treeT(root,targetSum);
return count;
}
void treeT(TreeNode root, int targetSum){
if(root == null)
return;
travel(root,targetSum,0);
treeT(root.left,targetSum);
treeT(root.right,targetSum);
}
void travel(TreeNode root,int targetSum,int sum){
if(root == null)
return;
sum += root.val;
if(sum == targetSum)
count++;
travel(root.left,targetSum,sum);
travel(root.right,targetSum,sum);
}
}
/*动态规划思路:
定义一个数组res,长度为2,res[0]表示不抢该节点可获得最大值,
res[1]表示抢劫该节点可获得最大值
方法helper(r)意为:在以r为根节点的树中,返回抢劫根节点与不抢劫根节点可获得的最大值
*/
class Solution {
public int rob(TreeNode root) {
int[] res = helper(root);
return Math.max(res[0],res[1]);
}
public int[] helper(TreeNode r){
if(r == null) return new int[2];
//边界条件,r为null时,跳出
int[] left = helper(r.left);
/*对于以r.left为根的树,计算抢劫根节点(r.left)与不抢劫根节点可获得最大金额.
left[0]则为不抢r.lrft可获得的最大金额,left[1]则为抢劫r.left可获得的最大金额
以下right[] 分析同理*/
int[] right = helper(r.right);
int[] res = new int[2];
res[0] = Math.max(left[0],left[1]) + Math.max(right[0],right[1]);
//计算不抢劫当前根节点可获得的最大金额(那么其左右子树可以随便抢)
res[1] = r.val + left[0] + right[0];
//计算若抢劫根节点可获得的最大金额(此时,其左右子树的根节点不能被抢)
return res;
}
}