0

I'm currently working on leetcode problem 366 where we have to find list of lists that contains values of leaves of each generation. I wanted to achieve this by recursion where if a node does not have left or right child, the value is recorded then the node removed by setting it to None. Here is my code:

def findLeaves(self, root: Optional[TreeNode]) -> List[List[int]]:
 leaf_list = []
 sub_list = []
 def traverse(node):
 if node == None:
 return
 if node.left == None and node.right == None:
 sub_list.append(node.val)
 node = None
 return 
 traverse(node.left)
 traverse(node.right)
 return root
 
 while True:
 if root == None:
 break
 sub_list = []
 traverse(root)
 leaf_list.append(sub_list)
 print(leaf_list)
 return leaf_list

The problem seems to be that when a certain node is set to None, that change isn't retained. Why is it that I can't set a node to None to remove it?

Thanks

asked Jan 26, 2022 at 19:14
3
  • There is a difference between changing node and changing the part of the tree that points to node. Commented Jan 26, 2022 at 19:17
  • could you please elaborate on that? If at 3rd recursion node is root.left.left.left and that node is an instance of class TreeNode, wouldn't setting node = None equate removing root.left.left.left? Commented Jan 26, 2022 at 19:32
  • Obviously not, or you wouldn't be here. If you want root.left.left.left to be None, you have to assign None to that. Commented Jan 26, 2022 at 20:00

1 Answer 1

1

The tree can only be mutated when you assign to one if its node's attributes. An assignment to a variable, only changes what the variable represents. Such assignment never impacts whatever previous value that variable had. Assigning to a variable is like switching from one value to another without affecting any data structure. So you need to adapt your code such that the assignment of None is done to a left or right attribute.

The exception is for the root node itself. When the root is a leaf, then there is no parent to mutate. You will then just discard the tree and switch to an empty one (None).

One way to achieve this, is to use the return value of traverse to update the child-reference (left or right) that the caller of traverse needs to update.

Here is your code with those adaptations:

def findLeaves(root):
 sub_list = []
 def traverse(node):
 if not node:
 return
 if not node.left and not node.right:
 sub_list.append(node.val)
 return # By returning None, the parent can remove it
 node.left = traverse(node.left) # Assign the returned node reference
 node.right = traverse(node.right)
 return node # Return the node (parent does not need to remove it)
 
 leaf_list = []
 while root:
 sub_list = []
 root = traverse(root)
 leaf_list.append(sub_list)
 return leaf_list
answered Jan 27, 2022 at 12:50
Sign up to request clarification or add additional context in comments.

Comments

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.