AlgoMaster Logo

Kth Smallest Element in a BST

Last Updated: March 29, 2026

medium
4 min read

Understanding the Problem

We have a binary search tree and need to find the kth smallest element in it. Since it's a BST, there's an implicit sorted order hiding in the tree structure. An in-order traversal (left, root, right) visits BST nodes in ascending order. So the kth node visited during an in-order traversal is our answer.

The real question is how efficiently we can get to that kth node. A naive approach would collect all values into a sorted list and pick the kth one. But we can do better by stopping the traversal as soon as we've visited k nodes, without needing to process the entire tree.

Key Constraints:

  • 1 <= k <= n <= 10^4 → k is always valid (never larger than the number of nodes). We don't need to handle the case where k exceeds the tree size. With n up to 10,000, even O(n) approaches are fine.
  • 0 <= Node.val <= 10^4 → Non-negative integer values. No overflow concerns.
  • The tree is guaranteed to be a valid BST, so in-order traversal will always yield sorted values.

Approach 1: In-Order Traversal (Store All Values)

Intuition

The most straightforward approach exploits the fundamental property of a BST: an in-order traversal produces values in ascending order. If we collect all values into a list via in-order traversal, the kth smallest is simply the element at index k-1.

This is the approach most people think of first. It's correct and easy to implement, but it does more work than necessary because it traverses the entire tree even if k is 1.

Algorithm

  1. Perform a complete in-order traversal of the BST.
  2. Store each node's value in a list as you visit it.
  3. Return the element at index k - 1 from the list.

Example Walkthrough

1Start: in-order traversal collects all values
3root124
1/5

Code

This works correctly but always traverses the entire tree and stores all values. What if we stopped the moment we found the kth element instead of collecting everything first?

Approach 2: Recursive In-Order with Early Stopping

Intuition

We know in-order traversal visits BST nodes in ascending order. Instead of collecting all values and then picking the kth one, we can count as we traverse and stop the moment our count reaches k.

The idea is simple: maintain a counter that increments each time we "visit" a node (the middle step of in-order). When the counter hits k, we've found our answer. The trick in the recursive version is propagating this early termination. We use class-level variables (or pass state by reference) to track the count and result across recursive calls.

Algorithm

  1. Initialize a counter at 0 and a variable to hold the result.
  2. Start an in-order traversal from the root.
  3. Recurse into the left subtree.
  4. Increment the counter. If it equals k, record the current node's value as the result and stop further processing.
  5. If the result hasn't been found yet, recurse into the right subtree.

Example Walkthrough

1Start in-order traversal: go left from root (5)
5root32146
1/5

Code

The recursive early-stop works well, but the termination isn't perfectly clean since returning only exits the current call frame. What if we used an iterative approach with an explicit stack so we could return the answer immediately?

Approach 3: Iterative In-Order Traversal with Stack

Intuition

An iterative in-order traversal gives us the same ascending visit order as the recursive version, but with one significant advantage: we have full control over when to stop. The moment we've visited the kth node, we return immediately. No call stack to unwind, no extra recursive calls.

The iterative approach uses an explicit stack. We push nodes as we go left, then pop a node, "visit" it (decrement k), and if k reaches 0, that node's value is our answer. Otherwise, move to its right child and repeat the process.

Algorithm

  1. Initialize an empty stack and set the current node to root.
  2. While the stack is non-empty or the current node is not null:
    • Push the current node onto the stack and move to its left child. Keep going until you reach null.
    • Pop the top node from the stack. Decrement k.
    • If k is 0, return this node's value.
    • Otherwise, set the current node to the popped node's right child.
  3. Continue until k reaches 0.

Example Walkthrough

1Start: push 5, 3, 2, 1 going left. Stack=[5,3,2,1]
5321top46
1/4

Code