Binary Tree Vertical Order Traversal - Leetcode 314 - Python

NeetCodeIO · Intermediate ·⚡ Algorithms & Data Structures ·1y ago

Key Takeaways

The video demonstrates a solution to the Binary Tree Vertical Order Traversal problem on Leetcode 314 using a BFS approach with a hashmap to group nodes by column, implemented in Python.

Full Transcript

Hey everyone, welcome back and let's write some more neat code today. So today, let's solve the problem binary tree vertical order traversal, not level order traversal like you might be more used to. In this problem, we're given the root of a binary tree and the root might be null. So keep that in mind, but we want to return the vertical order traversal of the nodes, meaning from top to bottom, column by column, and we want to return the values. So in this example, we see the root over here and we see that in this column, let's call it column zero, we have these two nodes and then we have the nodes written three and then 15 in the order that they appear from top to bottom. But that's not the first array that we're going to return. You can see here in the output that the first one is the leftmost column. That does make sense. We return this column, then this one, then this one, and then this one. And the leftmost column, let's call it at column -1, is just 9. And then over here, column 1 is just 20. And column 2 over here is just seven. And we return them in that order. This is the first array, second array, third, and fourth. We return them in the form of a nested list. So that kind of gives you an idea of what the vertical order traversal actually is. But this last line might confuse you, which is to say, two nodes that are at the same row and the same column, the order of them should be from left to right. Because if they're at the same position, it might be kind of ambiguous. If you don't know what that means, let me just draw out a little picture to show you. Let's say we have a root node, a left child, a right child over here. Sorry, I kind of didn't draw that on the same level. But then let's say this guy has a right child. This guy has a left child. Now these are considered to be at the same column. Let's say zero and this is negative one and this is positive one. Cuz when I'm here and then I have a right child, I'm going to take my column and increment it by one. So this guy which is on level two, this is level one, this is level zero. This guy is at column zero. But this guy when we go left we take the current column and decrement it by one also bringing us to zero. So this node is on the same row and same column as this one. So it's ambiguous because this is obviously one column. This is the other column, the middle column. And then we have one column over here. With the middle column, what order do these nodes appear in? Well, this is the first one. But between these two, it's ambiguous. That's why they tell us we will read them from left to right. So this is second, this is the third one. So that's what they mean when they ask us this part. So now that we have a bit of an idea of what the problem is asking for, which honestly with this problem is one of the hardest parts. So don't feel too bad if you struggled with it. But now that we have an idea of what they're asking us, how do we go about solving this problem? Well, typically with tree problems, you don't really have to get too creative. Most of the time it's probably going to be related to DFS or BFS. And I believe this problem can actually be solved both ways, but I think the BFS approach is a lot more intuitive. And I'll tell you why. Think about what we're doing with this problem. Each of these columns is going top to bottom, like the individual nodes in that column. If there's a tie, we want to go left to right. Well, BFS basically gives us both of these properties. BFS, which is actually a level order traversal, not vertical. It's going to go level by level. First level, then the second level, then the third level. So you have that top tobottom component of it, but also within a level, we're going left to right. Now, we could go the other way if we wanted to, but with this problem, it makes it pretty clear that we want to go left to right because with these two, we want this guy to go first and this guy to go second. So with that we can actually solve this problem relatively simply and as we do the BFS we just want to maintain the the current node and we want to maintain the column of every single node because we already know we're going to go top to bottom we're going to make sure to visit this level after the previous one and this one after the previous one so that this node will be added first and then these nodes. But we also want to be able to group these nodes together. And we'll do that by maintaining the column of each node. And then we'll be able to know that this node is not in the same column. This node is also in a different column. That's more or less the intuition. Now, one thing to keep in mind is how are we going to build these lists of lists? In terms of grouping nodes together within a certain column, it's not as straightforward as building the list of lists because we don't know the range of columns that's actually available to us. So, you know, you could say this is zero, but how do you know that -1 is going to be in bounds of this array, the outer array that is? Well, that's why it's probably better to use a hashmap for this problem where we take a column. So like this one, the index of the column and map it to an array or a list. This makes it pretty straightforward for us. And then at the end, we can kind of collect those lists together and then return it in the form that we actually want. So I think that's enough for us to now get into the dry run. So let's say we're given a tree that looks like this. And I'll go ahead and draw the hashmap as well. will map each column to let's say the list of values in that column. And I won't draw out like the whole Q BFS part. If you're not familiar with BFS, I highly recommend checking out some of the resources on neatcode.io. Those will walk you through that pretty in-depth and you'll definitely want a good understanding of this algorithm. It comes up quite a lot and if you understand it, this problem becomes pretty trivial. Let me show you what I mean. So let's say we start here and let's say that that's column zero. We're going to go ahead and map it in our hashmap to zero. And then we're going to create a list here. And the first value in that list is going to be one. And then we're going to go to the two children that do exist. We'll end up adding them to the queue as well. This one is going to be at -1. This one is going to be at positive one. We'll go left to right. Pop this one. It's at column 1. And we will map that to two over here. We'll do the same thing after popping this. We'll map it to one. And the value of that is three. So we'll do that. This one didn't have any children. This one does have two children. Left child is going to be at column zero. Right child is going to be at column two. Let's go ahead and take the four. This time it's at a column that already exists. So we will take that four and append it to this list over here. We get that four. Next we do this one and it's at column 2. So here we will add five to that column. And then this one does have a child. left child is going to be at 2 minus one column one. We'll take this six and it's over here. This is the column and we'll add it to the list over here. And then we're pretty much done. There's no more nodes for us to do. So these are the lists that we have. Now we want to collect them in a specific order. We want the minimum column to go first and then the next one, then the next one, and then the next one. So what you could do is just find the smallest column in this hashmap and then just keep incrementing by one until you can't really go any further until we get like a key doesn't exist. Um another way to do it though would be as we're doing this maintain what's the minimum column that we have seen so far and what is the max column that we've seen so far and then you know you can iterate from this one to this one cuz the range of course is going to be contiguous. we don't expect like one of these columns to just not exist, then our tree would be like non-ontiguous. It would be kind of weird. That's not really possible. Um, so then we can just go from negative 1 to two and then just keep collecting each of these lists and then add it to an outer list and then that is what we end up returning. So this way we will visit each node once, we'll end up adding each node to the hashmap at most once. So space and time complexity is going to be linear. So with that said, let's code this up now. So the first thing I'm going to start out with is actually the case where the root does not exist because that is a possibility. And in that case, we can just return an empty list. There's no need to do any sort of traversal. Otherwise, we're going to have our Q, and it's going to be a double-ended Q in Python. And I'm going to initialize it with a tupil, which is going to include the root node, which now we know is not null. And the second is going to be a number which is going to correspond to the column of that node. And like I said, I'm also going to maintain what the minimum column and max column are. That's going to make things easier for us at the end. And initially, we can say that these are both zero because we know that definitely the zeroth column does exist the way that we've defined this. And lastly, we're going to have the hashmap, which is very important. Let's just call it calls columns the plural. And I'm going to use a default dictionary in Python. If you're not familiar with this, highly recommend checking out Python for coding interviews course. It'll walk you through exactly how to use this. But basically, it's a hashmap where the default value is going to be a list in this case. That's the way I've set it up. And we're specifically going to map each column index to the list of values of that column. So then we can return them at the end after we've converted it to a list of lists. So now let's get started with the BFS. while our Q is non- empty pop from the Q and we're going to get a couple values. We're going to get the node and the column. Um I guess this is a good point to update our min and max column because every node is going to be pushed and popped. So we can say our min column is going to be the min of itself as well as the uh column that we're given. And then we'll have the max column which is going to be the max of itself and the column. That's just a little bit of bookkeeping. But the next part is where we take now the value of this node and add it to our hashmap using the column as a key. So calls the plural and then we'll use the current column that we have here. And then to that we're going to append the current nodes value. And then after that we can just check our two children. If my left child exists I'm going to do something which is um taking to the queue. We're going to append the tupil, the left child, and the index of that left child. Well, the column specifically. And this is kind of the important part. We're taking the current column and decrementing it by one when we go left. And I'll copy and paste this cuz the next part's going to be pretty similar. When we go right, we're going to append, of course, the right child, but then we're going to increment the current column. So that's probably the important part of this algorithm here. Now, after that's done, we want to return, but we can't just return the hashmap. We have to return it in the form of a list. I'm going to take advantage of list comprehension in Python. I also cover this in the Python for coding interviews course if you're interested. But what we're going to do is just iterate over uh the range of columns. So, from min column to max column. Let's say for CN range, min column to max column. This is non-inclusive in Python. So I'm going to add a plus one there. So we're iterating over the columns in the order that we want them. And then I'm just going to take from the columns hashmap get the column at the current index. And then we'll add that to this list. So we'll have them in the order that we want and it'll also be in the form that we want. So let me go ahead and return this or sorry execute it. And you can see here it works and it is very efficient. I don't think there's a big difference between 3 milliseconds and this one. The overall time complexity is definitely the same and this is the optimal solution for BFS. If you found this helpful, check out neatcode.io for a lot more. Thanks for watching and I'll see you

Original Description

🚀 https://neetcode.io/ - A better way to prepare for Coding Interviews 🧑‍💼 LinkedIn: https://www.linkedin.com/in/navdeep-singh-3aaa14161/ 🐦 Twitter: https://twitter.com/neetcode1 ⭐ BLIND-75 PLAYLIST: https://www.youtube.com/watch?v=KLlXCFG5TnA&list=PLot-Xpze53ldVwtstag2TL4HQhAnC8ATf Problem Link: https://leetcode.com/problems/binary-tree-vertical-order-traversal/description/ 0:00 - Read the problem 0:30 - Drawing Explanation 8:20 - Coding Explanation leetcode 314 #neetcode #leetcode #python
Watch on YouTube ↗ (saves to browser)
Sign in to unlock AI tutor explanation · ⚡30

Playlist

Uploads from NeetCodeIO · NeetCodeIO · 0 of 60

← Previous Next →
1 Leetcode 149 - Maximum Points on a Line - Python
Leetcode 149 - Maximum Points on a Line - Python
NeetCodeIO
2 Design Linked List - Leetcode 707 - Python
Design Linked List - Leetcode 707 - Python
NeetCodeIO
3 Minimum Time to Collect All Apples in a Tree - Leetcode 1443 - Python
Minimum Time to Collect All Apples in a Tree - Leetcode 1443 - Python
NeetCodeIO
4 Design Browser History - Leetcode 1472 - Python
Design Browser History - Leetcode 1472 - Python
NeetCodeIO
5 Number of Good Paths - Leetcode 2421 - Python
Number of Good Paths - Leetcode 2421 - Python
NeetCodeIO
6 Flip String to Monotone Increasing - Leetcode 926 - Python
Flip String to Monotone Increasing - Leetcode 926 - Python
NeetCodeIO
7 Maximum Sum Circular Subarray - Leetcode 918 - Python
Maximum Sum Circular Subarray - Leetcode 918 - Python
NeetCodeIO
8 Find Closest Node to Given Two Nodes - Leetcode 2359 - Python
Find Closest Node to Given Two Nodes - Leetcode 2359 - Python
NeetCodeIO
9 Concatenated Words - Leetcode 472 - Python
Concatenated Words - Leetcode 472 - Python
NeetCodeIO
10 Data Stream as Disjoint Intervals - Leetcode 352 - Python
Data Stream as Disjoint Intervals - Leetcode 352 - Python
NeetCodeIO
11 LFU Cache - Leetcode 460 - Python
LFU Cache - Leetcode 460 - Python
NeetCodeIO
12 N-th Tribonacci Number - Leetcode 1137
N-th Tribonacci Number - Leetcode 1137
NeetCodeIO
13 Best Team with no Conflicts - Leetcode 1626 - Python
Best Team with no Conflicts - Leetcode 1626 - Python
NeetCodeIO
14 Greatest Common Divisor of Strings - Leetcode 1071 - Python
Greatest Common Divisor of Strings - Leetcode 1071 - Python
NeetCodeIO
15 Shortest Path in a Binary Matrix - Leetcode 1091 - Python
Shortest Path in a Binary Matrix - Leetcode 1091 - Python
NeetCodeIO
16 Insert into a Binary Search Tree - Leetcode 701 - Python
Insert into a Binary Search Tree - Leetcode 701 - Python
NeetCodeIO
17 Delete Node in a BST - Leetcode 450 - Python
Delete Node in a BST - Leetcode 450 - Python
NeetCodeIO
18 Shuffle the Array (Constant Space) - Leetcode 1470 - Python
Shuffle the Array (Constant Space) - Leetcode 1470 - Python
NeetCodeIO
19 Fruits into Basket - Leetcode 904 - Python
Fruits into Basket - Leetcode 904 - Python
NeetCodeIO
20 Number of Subarrays of size K and Average Greater than or Equal to Threshold - Leetcode 1343 Python
Number of Subarrays of size K and Average Greater than or Equal to Threshold - Leetcode 1343 Python
NeetCodeIO
21 Naming a Company - Leetcode 2306 - Python
Naming a Company - Leetcode 2306 - Python
NeetCodeIO
22 As Far from Land as Possible - Leetcode 1162 - Python
As Far from Land as Possible - Leetcode 1162 - Python
NeetCodeIO
23 Shortest Path with Alternating Colors - Leetcode 1129 - Python
Shortest Path with Alternating Colors - Leetcode 1129 - Python
NeetCodeIO
24 Minimum Fuel Cost to Report to the Capital - Leetcode 2477 - Python
Minimum Fuel Cost to Report to the Capital - Leetcode 2477 - Python
NeetCodeIO
25 Count Odd Numbers in an Interval Range - Leetcode 1523 - Python
Count Odd Numbers in an Interval Range - Leetcode 1523 - Python
NeetCodeIO
26 Contains Duplicate II - Leetcode 219 - Python
Contains Duplicate II - Leetcode 219 - Python
NeetCodeIO
27 Path with Maximum Probability - Leetcode 1514 - Python
Path with Maximum Probability - Leetcode 1514 - Python
NeetCodeIO
28 Add to Array-Form of Integer - Leetcode 989 - Python
Add to Array-Form of Integer - Leetcode 989 - Python
NeetCodeIO
29 Unique Paths II - Leetcode 63 - Python
Unique Paths II - Leetcode 63 - Python
NeetCodeIO
30 Minimum Distance between BST Nodes - Leetcode 783 - Python
Minimum Distance between BST Nodes - Leetcode 783 - Python
NeetCodeIO
31 Design Hashmap - Leetcode 706 - Python
Design Hashmap - Leetcode 706 - Python
NeetCodeIO
32 Range Sum Query Immutable - Leetcode 303 - Python
Range Sum Query Immutable - Leetcode 303 - Python
NeetCodeIO
33 Binary Tree Zigzag Level Order Traversal - Leetcode 103 - Python
Binary Tree Zigzag Level Order Traversal - Leetcode 103 - Python
NeetCodeIO
34 Middle of the Linked List - Leetcode 876 - Python
Middle of the Linked List - Leetcode 876 - Python
NeetCodeIO
35 Course Schedule IV - Leetcode 1462 - Python
Course Schedule IV - Leetcode 1462 - Python
NeetCodeIO
36 Single Element in a Sorted Array - Leetcode 540 - Python
Single Element in a Sorted Array - Leetcode 540 - Python
NeetCodeIO
37 Capacity to Ship Packages - Leetcode 1011 - Python
Capacity to Ship Packages - Leetcode 1011 - Python
NeetCodeIO
38 IPO - Leetcode 502 - Python
IPO - Leetcode 502 - Python
NeetCodeIO
39 Minimize Deviation in Array - Leetcode 1675 - Python
Minimize Deviation in Array - Leetcode 1675 - Python
NeetCodeIO
40 Longest Turbulent Array - Leetcode 978 - Python
Longest Turbulent Array - Leetcode 978 - Python
NeetCodeIO
41 Last Stone Weight II - Leetcode 1049 - Python
Last Stone Weight II - Leetcode 1049 - Python
NeetCodeIO
42 Construct Quad Tree - Leetcode 427 - Python
Construct Quad Tree - Leetcode 427 - Python
NeetCodeIO
43 Find Duplicate Subtrees - Leetcode 652 - Python
Find Duplicate Subtrees - Leetcode 652 - Python
NeetCodeIO
44 Sort an Array - Leetcode 912 - Python
Sort an Array - Leetcode 912 - Python
NeetCodeIO
45 Ones and Zeroes - Leetcode 474 - Python
Ones and Zeroes - Leetcode 474 - Python
NeetCodeIO
46 Remove Duplicates from Sorted Array II - Leetcode 80 - Python
Remove Duplicates from Sorted Array II - Leetcode 80 - Python
NeetCodeIO
47 Maximum Twin Sum of a Linked List - Leetcode 2130 - Python
Maximum Twin Sum of a Linked List - Leetcode 2130 - Python
NeetCodeIO
48 Concatenation of Array - Leetcode 1929 - Python
Concatenation of Array - Leetcode 1929 - Python
NeetCodeIO
49 Symmetric Tree - Leetcode 101 - Python
Symmetric Tree - Leetcode 101 - Python
NeetCodeIO
50 Check Completeness of a Binary Tree - Leetcode 958 - Python
Check Completeness of a Binary Tree - Leetcode 958 - Python
NeetCodeIO
51 Construct Binary Tree from Inorder and Postorder Traversal - Leetcode 106 - Python
Construct Binary Tree from Inorder and Postorder Traversal - Leetcode 106 - Python
NeetCodeIO
52 Find Peak Element - Leetcode 162 - Python
Find Peak Element - Leetcode 162 - Python
NeetCodeIO
53 Accounts Merge - Leetcode 721 - Python
Accounts Merge - Leetcode 721 - Python
NeetCodeIO
54 Binary Tree Preorder Traversal (Iterative) - Leetcode 144 - Python
Binary Tree Preorder Traversal (Iterative) - Leetcode 144 - Python
NeetCodeIO
55 Binary Tree Postorder Traversal (Iterative) - Leetcode 145 - Python
Binary Tree Postorder Traversal (Iterative) - Leetcode 145 - Python
NeetCodeIO
56 Number of Zero-Filled Subarrays - Leetcode 2348 - Python
Number of Zero-Filled Subarrays - Leetcode 2348 - Python
NeetCodeIO
57 Minimum Score of a Path Between Two Cities - Leetcode 2492 - Python
Minimum Score of a Path Between Two Cities - Leetcode 2492 - Python
NeetCodeIO
58 Sqrt(x) - Leetcode 69 - Python
Sqrt(x) - Leetcode 69 - Python
NeetCodeIO
59 Successful Pairs of Spells and Potions - Leetcode 2300 - Python
Successful Pairs of Spells and Potions - Leetcode 2300 - Python
NeetCodeIO
60 Optimal Partition of String - Leetcode 2405 - Python
Optimal Partition of String - Leetcode 2405 - Python
NeetCodeIO

This video teaches how to solve the Binary Tree Vertical Order Traversal problem using a BFS approach with a hashmap, and provides a Python implementation. The problem requires returning the vertical order traversal of nodes in a binary tree, and the solution involves using a queue to perform BFS and a hashmap to group nodes by column.

Key Takeaways
  1. Create a hashmap to map column values to lists of nodes
  2. Pop nodes from the queue and map them to their respective column values
  3. Append nodes to their corresponding lists in the hashmap
  4. Collect lists of nodes in ascending order of column values
  5. Use a double-ended queue to perform BFS with the root node and its column as the initial values
  6. Update the minimum and maximum column after each node is popped from the queue
  7. Add the node's value to the hashmap using the column as a key
💡 Using a hashmap to group nodes by column allows for efficient vertical order traversal of the binary tree.

Related AI Lessons

Bloom Filters, Explained Properly
Learn how Bloom filters work and their benefits, including tiny memory and blazing speed, in exchange for potential false positives.
Dev.to · Daksh Gargas
Prefix Sums: The Preprocessing Trick That Makes Range Queries Instant
Learn how prefix sums enable instant range queries in arrays, boosting performance in various applications
Medium · Programming
I Thought I Was Ready for the Interview — Then One Simple Math Question Destroyed Me
A simple math question can destroy a developer's interview, highlighting the importance of being prepared for unexpected questions
Medium · Programming
Week 2(Day 10): LeetCode Two Pointers(slow & fast): Remove Duplicates from Sorted Array (Brute…
Learn to remove duplicates from a sorted array using the two pointers technique, improving from brute force to optimized solutions
Medium · Python

Chapters (3)

Read the problem
0:30 Drawing Explanation
8:20 Coding Explanation
Up next
Stump Grinder Carbide Wheel Grinds Hardwood To Chips
Innoforge Studio
Watch →