Given the root
of a binary tree and an integer targetSum
, return the number of paths where the sum of the values along the path equals targetSum
.
The path does not need to start or end at the root or a leaf, but it must go downwards (i.e., traveling only from parent nodes to child nodes).
Example 1:
Input: root = [10,5,-3,3,2,null,11,3,-2,null,1], targetSum = 8 Output: 3 Explanation: The paths that sum to 8 are shown.
Example 2:
Input: root = [5,4,8,11,null,13,4,7,2,null,null,5,1], targetSum = 22 Output: 3
Constraints:
- The number of nodes in the tree is in the range
[0, 1000]
. -109 <= Node.val <= 109
-1000 <= targetSum <= 1000
给定一棵二叉树和一个目标数,问存在多少条路径,这些路径上的所有节点值的和等于目标数。路径不一定要始于根节点终于叶节点,但是路径必须要是从上往下的。
先来看一个特殊情况,即二叉树从根节点到叶节点只有一条路径,那么就是求这条路径上存在几条子路径的和等于目标数。那就跟一个数组里存在几个子数组的和等于目标数一样了,我们知道任意一个子数组的和等于‘子数组终点到数组的起点的和’减去‘子数组起点的前一个点到数组起点的和’。如果把所有起点到所有经过的点的和都存在一个dict里(由于可能存在重复值,dict用于记录和相同的个数 )那么通过判断起点到当前点的和与目标数的差值是否在dict就可以知道是否存在以及存在几个子数组的和等于目标数。
对于只有一条总路径的二叉树可以用以上方法做同样处理。而对于任意二叉树可以用前序遍历的递归算法,因为前序遍历每次走的都是从根节点到一个叶节点的路径,这样对于每条根节点到叶节点的路径就也可以做跟数组类似的处理。需要注意的是在递归调用返回时,dcit中记录当前和个数要减去1再返回到上一层。
class Solution:
def pathSum(self, root: Optional[TreeNode], targetSum: int) -> int:
if not root:
return 0
res = 0
sumDict = collections.defaultdict(int)
sumDict[0] = 1
def helper(node, sum):
if not node:
return
nonlocal res, sumDict
sum += node.val
if sum - targetSum in sumDict:
res += sumDict[sum - targetSum]
sumDict[sum] += 1
helper(node.left, sum)
helper(node.right, sum)
sumDict[sum] -= 1
helper(root, 0)
return res