BST Find Minimum Element in DSA C++ - Time & Space Complexity
We want to understand how long it takes to find the smallest value in a Binary Search Tree (BST).
How does the time needed change as the tree grows bigger?
Analyze the time complexity of the following code snippet.
Node* findMin(Node* root) {
if (root == nullptr) return nullptr;
while (root->left != nullptr) {
root = root->left;
}
return root;
}
This code finds the minimum element by going left until no more left child exists.
Identify the loops, recursion, array traversals that repeat.
- Primary operation: Moving from a node to its left child repeatedly.
- How many times: At most once per level down the left side of the tree.
As the tree grows, the time depends on the height of the leftmost path.
| Input Size (n) | Approx. Operations |
|---|---|
| 10 | Up to 4 steps (if tree is balanced) |
| 100 | Up to 7 steps (balanced tree height) |
| 1000 | Up to 10 steps (balanced tree height) |
Pattern observation: In a balanced tree, steps grow slowly with size (logarithmically). In a skewed tree, steps can grow linearly.
Time Complexity: O(h) where h is the tree height
This means the time depends on how tall the tree is, not just how many nodes it has.
[X] Wrong: "Finding minimum always takes the same time regardless of tree shape."
[OK] Correct: If the tree is very unbalanced (like a linked list), it takes longer because you must go through many nodes.
Understanding how tree shape affects search time is a key skill for working with trees and helps you explain your code clearly in interviews.
"What if the tree was balanced using a self-balancing method? How would the time complexity change?"
Practice
Solution
Step 1: Understand BST property
In a BST, left child nodes have smaller values than their parents.Step 2: Locate minimum element
The smallest value is found by going left until no more left child exists.Final Answer:
At the leftmost node -> Option BQuick Check:
Minimum = leftmost node [OK]
- Thinking minimum is at root
- Confusing leftmost with rightmost
- Assuming minimum can be any leaf
root?Solution
Step 1: Check traversal direction
Minimum is found by moving left until no left child exists.Step 2: Verify code correctness
while(root->left != nullptr) root = root->left; return root->data; loops left correctly and returns the leftmost node's data.Final Answer:
while(root->left != nullptr) root = root->left; return root->data; -> Option AQuick Check:
Traverse left to find minimum [OK]
- Looping right child instead of left
- Returning root data without traversal
- Not checking for nullptr before access
struct Node {
int data;
Node* left;
Node* right;
};
Node* root = new Node{10, nullptr, nullptr};
root->left = new Node{5, nullptr, nullptr};
root->right = new Node{15, nullptr, nullptr};
root->left->left = new Node{2, nullptr, nullptr};
Node* temp = root;
while(temp->left != nullptr) {
temp = temp->left;
}
std::cout << temp->data << std::endl;Solution
Step 1: Trace the tree structure
Root is 10, left child 5, left-left child 2, right child 15.Step 2: Follow the loop to find minimum
Loop moves from 10 to 5, then to 2, which has no left child.Final Answer:
2 -> Option CQuick Check:
Leftmost node data = 2 [OK]
- Stopping at root or first left child
- Confusing right child as minimum
- Not tracing loop fully
int findMin(Node* root) {
if(root == nullptr) return -1;
while(root->right != nullptr) {
root = root->right;
}
return root->data;
}Solution
Step 1: Analyze loop direction
Minimum element is found by moving left, not right.Step 2: Identify incorrect traversal
The code loops on root->right, which finds maximum, not minimum.Final Answer:
Loops on right child instead of left child -> Option AQuick Check:
Minimum requires left traversal [OK]
- Using right child loop for minimum
- Ignoring nullptr checks
- Confusing min and max logic
Solution
Step 1: Understand edge case
If no left child exists, root itself is minimum.Step 2: Modify search logic
Traverse left until nullptr; if none found, root is minimum.Final Answer:
Traverse left child until nullptr; if none, root is minimum -> Option DQuick Check:
Minimum = leftmost or root if no left child [OK]
- Assuming minimum always has left child
- Traversing right child for minimum
- Not handling single-child nodes
Ready to prove it?
Pass the test and this pattern moves unknown
