🧠
Optimal (Inorder Simulation with Index Pointer)
💡 This approach simulates inorder traversal to build the BST in O(n) time without slicing arrays, improving space efficiency.
Intuition
Use recursion to build left subtree of size n/2, then create root from middle element, then build right subtree. This simulates inorder traversal.
Algorithm
- Maintain a global or external index pointer starting at 0.
- Recursively build left subtree from left to mid-1.
- Create root node with nums[mid].
- Increment index pointer.
- Recursively build right subtree from mid+1 to right.
- Return root node.
💡 This approach avoids slicing arrays, which can be costly, by using index pointers and simulating inorder traversal.
class TreeNode:
def __init__(self, val=0, left=None, right=None):
self.val = val
self.left = left
self.right = right
class Solution:
def __init__(self):
self.index = 0
def helper(self, nums, left, right):
if left > right:
return None
mid = (left + right) // 2
left_child = self.helper(nums, left, mid - 1)
root = TreeNode(nums[mid])
self.index += 1
root.left = left_child
root.right = self.helper(nums, mid + 1, right)
return root
def sorted_array_to_bst(self, nums):
self.index = 0
return self.helper(nums, 0, len(nums) - 1)
# Driver code
if __name__ == '__main__':
nums = [-10, -3, 0, 5, 9]
sol = Solution()
root = sol.sorted_array_to_bst(nums)
def inorder(node):
return inorder(node.left) + [node.val] + inorder(node.right) if node else []
print(inorder(root))
Line Notes
class TreeNode:Defines BST node structure
class Solution:Encapsulates index pointer and helper method
self.index = 0Reset index before recursion
def helper(self, nums, left, right):Recursive helper to build BST simulating inorder traversal
if left > right:Base case: no elements left
mid = (left + right) // 2Calculate middle index
left_child = self.helper(nums, left, mid - 1)Build left subtree first to simulate inorder
root = TreeNode(nums[mid])Create root node from middle element to maintain BST property
self.index += 1Increment index pointer after using element
root.left = left_childAssign left subtree
root.right = self.helper(nums, mid + 1, right)Build right subtree after root
return rootReturn constructed subtree root
def sorted_array_to_bst(self, nums):Entry function to start recursion
class TreeNode {
int val;
TreeNode left, right;
TreeNode(int val) { this.val = val; }
}
public class Solution {
int index = 0;
public TreeNode helper(int[] nums, int left, int right) {
if (left > right) return null;
int mid = (left + right) / 2;
TreeNode leftChild = helper(nums, left, mid - 1);
TreeNode root = new TreeNode(nums[mid]);
index++;
root.left = leftChild;
root.right = helper(nums, mid + 1, right);
return root;
}
public TreeNode sortedArrayToBST(int[] nums) {
index = 0;
return helper(nums, 0, nums.length - 1);
}
public static void inorder(TreeNode root) {
if (root == null) return;
inorder(root.left);
System.out.print(root.val + " ");
inorder(root.right);
}
public static void main(String[] args) {
Solution sol = new Solution();
int[] nums = {-10, -3, 0, 5, 9};
TreeNode root = sol.sortedArrayToBST(nums);
inorder(root);
}
}
Line Notes
class TreeNode {Defines BST node structure
int index = 0;Index pointer to track current element
public TreeNode helper(int[] nums, int left, int right) {Recursive helper simulating inorder traversal
if (left > right) return null;Base case: no elements left
int mid = (left + right) / 2;Calculate middle index
TreeNode leftChild = helper(nums, left, mid - 1);Build left subtree first
TreeNode root = new TreeNode(nums[mid]);Create root node from middle element
index++;Increment index after using element
root.left = leftChild;Assign left subtree
root.right = helper(nums, mid + 1, right);Build right subtree after root
return root;Return constructed subtree root
public TreeNode sortedArrayToBST(int[] nums) {Entry function to start recursion
index = 0;Reset index before recursion
#include <iostream>
#include <vector>
using namespace std;
struct TreeNode {
int val;
TreeNode* left;
TreeNode* right;
TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
};
class Solution {
public:
int index = 0;
TreeNode* helper(const vector<int>& nums, int left, int right) {
if (left > right) return nullptr;
int mid = (left + right) / 2;
TreeNode* leftChild = helper(nums, left, mid - 1);
TreeNode* root = new TreeNode(nums[mid]);
index++;
root->left = leftChild;
root->right = helper(nums, mid + 1, right);
return root;
}
TreeNode* sortedArrayToBST(vector<int>& nums) {
index = 0;
return helper(nums, 0, nums.size() - 1);
}
};
void inorder(TreeNode* root) {
if (!root) return;
inorder(root->left);
cout << root->val << " ";
inorder(root->right);
}
int main() {
vector<int> nums = {-10, -3, 0, 5, 9};
Solution sol;
TreeNode* root = sol.sortedArrayToBST(nums);
inorder(root);
cout << endl;
return 0;
}
Line Notes
struct TreeNode {Defines BST node structure
int index = 0;Index pointer to track current element
TreeNode* helper(const vector<int>& nums, int left, int right) {Recursive helper simulating inorder traversal
if (left > right) return nullptr;Base case: no elements left
int mid = (left + right) / 2;Calculate middle index
TreeNode* leftChild = helper(nums, left, mid - 1);Build left subtree first
TreeNode* root = new TreeNode(nums[mid]);Create root node from middle element
index++;Increment index after using element
root->left = leftChild;Assign left subtree
root->right = helper(nums, mid + 1, right);Build right subtree after root
return root;Return constructed subtree root
TreeNode* sortedArrayToBST(vector<int>& nums) {Entry function to start recursion
index = 0;Reset index before recursion
class TreeNode {
constructor(val=0, left=null, right=null) {
this.val = val;
this.left = left;
this.right = right;
}
}
class Solution {
constructor() {
this.index = 0;
}
helper(nums, left, right) {
if (left > right) return null;
const mid = Math.floor((left + right) / 2);
const leftChild = this.helper(nums, left, mid - 1);
const root = new TreeNode(nums[mid]);
this.index++;
root.left = leftChild;
root.right = this.helper(nums, mid + 1, right);
return root;
}
sortedArrayToBST(nums) {
this.index = 0;
return this.helper(nums, 0, nums.length - 1);
}
}
// Driver code
const nums = [-10, -3, 0, 5, 9];
const sol = new Solution();
const root = sol.sortedArrayToBST(nums);
function inorder(node) {
if (!node) return [];
return [...inorder(node.left), node.val, ...inorder(node.right)];
}
console.log(inorder(root));
Line Notes
class TreeNode {Defines BST node structure
constructor() {Initialize index pointer
this.index = 0;Reset index before recursion
helper(nums, left, right) {Recursive helper simulating inorder traversal
if (left > right) return null;Base case: no elements left
const mid = Math.floor((left + right) / 2);Calculate middle index
const leftChild = this.helper(nums, left, mid - 1);Build left subtree first
const root = new TreeNode(nums[mid]);Create root node from middle element
this.index++;Increment index after using element
root.left = leftChild;Assign left subtree
root.right = this.helper(nums, mid + 1, right);Build right subtree after root
return root;Return constructed subtree root
Each element is processed once. Recursion stack depth is O(log n) due to balanced tree construction.
💡 For n=20, about 20 operations and recursion depth 4-5, efficient and minimal overhead.
Interview Verdict: Accepted and optimal
This approach is optimal in time and space, especially for large inputs, and avoids extra array slicing.