You are given a binary tree in which each node contains an integer value.
Find the number of paths that sum to a given value.
The path does not need to start or end at the root or a leaf, but it must go downwards (traveling only from parent nodes to child nodes).
The tree has no more than 1,000 nodes and the values are in the range -1,000,000 to 1,000,000.
Example:
root = [10,5,-3,3,2,null,11,3,-2,null,1], sum = 8 10 / 5 -3 / 3 2 11 / 3 -2 1 Return 3. The paths that sum to 8 are: 1. 5 -> 3 2. 5 -> 2 -> 1 3. -3 -> 11
Solution:
1.use iterative way; BFS; use hashmap to store each node's previous path sum and its number (each previous path start from the root to itself, and each children node to itself)
1 if not root: 2 return 0 3 4 ans = 0 5 innerHash= {root.val:1} 6 d = [] 7 d.append((root, innerHash)) 8 9 while (len(d)): 10 nodeInfo = d.pop(0) 11 node = nodeInfo[0] 12 innerHash = nodeInfo[1] 13 14 if sum in innerHash: 15 ans += innerHash[sum] 16 #print ("get sum: ", node.val, innerHash) 17 if node.left: 18 tmpHash = defaultdict(lambda: 0) 19 for k in innerHash: 20 tmpHash[k+node.left.val] = innerHash[k] 21 tmpHash[node.left.val] += 1 22 d.append((node.left, tmpHash)) 23 if node.right: 24 tmpHash = defaultdict(lambda: 0) 25 for k in innerHash: 26 tmpHash[k+node.right.val] = innerHash[k] 27 28 tmpHash[node.right.val] += 1 29 d.append((node.right, tmpHash)) 30 31 return ans
2. use recursive way
1 def find_paths(root, target): 2 if root: 3 return int(root.val == target) + find_paths(root.left, target-root.val) + find_paths(root.right, target-root.val) 4 return 0 5 6 if root: 7 return find_paths(root, sum) + self.pathSum(root.left, sum) + self.pathSum(root.right, sum) 8 return 0
Extensions by myself:
if we want to print all the paths.
#record each node path from "root", if current path sum is bigger than the given sum, pop the first element in the list ("root")
# get the continuous subsum; considering there is '0' element or negative element, so there is possible multiple indexes returned.
1 def getSubSum(innerLst, s): 2 tmpS = 0 3 lstInd = [] 4 for i in range(len(innerLst)-1, -1, -1): 5 tmpS += innerLst[i] 6 if tmpS == s: 7 lstInd.append(i) #return the start index that make the sum of element equal to s from start index to the end 8 return lstInd 9 10 if root is None: 11 return 0 12 d = [] 13 s = sum 14 innerLst = [root.val] 15 ansLst = [] 16 d.append((root, innerLst)) 17 18 while (len(d)): 19 #pop 20 nodeInfo = d.pop(0) 21 node = nodeInfo[0] 22 innerLst = nodeInfo[1] 23 #print ("node: ", node.val, innerLst) 24 sumPath = 0 25 for e in innerLst: 26 sumPath+=e 27 28 lstInd = getSubSum(innerLst, s) 29 #print ("get sum: ", innerLst, lstInd) 30 for startInd in lstInd: 31 ansLst.append(innerLst[startInd::]) 32 33 #print ("updated: ", node.val, innerLst) 34 if node.left: 35 d.append((node.left, innerLst + [node.left.val])) 36 if node.right: 37 d.append((node.right, innerLst + [node.right.val])) 38 #print ("ans: ", ansLst) 39 #return ansLst 40 return len(ansLst)