The problem can be found at the following link: Question Link
Given the root of a binary tree, check whether it is a Binary Search Tree (BST) or not.
- The left subtree of a node contains only nodes with keys less than the node's key.
- The right subtree of a node contains only nodes with keys greater than the node's key.
- Both the left and right subtrees must also be binary search trees.
- Note: BSTs cannot contain duplicate nodes.
root = [2, 1, 3, N, N, N, 5]

true
- The left subtree of every node contains smaller keys and right subtree of every node contains greater keys. Hence, it is a BST.
root = [2, N, 7, N, 6, N, 9]

false
- Since the node to the right of node with key
7
has lesser key value,
Hence, it is not a BST.
root = [10, 5, 20, N, N, 9, 25]

false
- The node with key
9
present in the right subtree has lesser key value than root node.
Hence, it is not a BST.
- 1 ≤ Number of nodes ≤
$10^5$ - 1 ≤ node->data ≤
$10^9$
-
Base Case:
- If the current node is
NULL
, returntrue
(an empty tree is a valid BST).
- If the current node is
-
Check Current Node:
- The current node’s value should be greater than the
min
value and less than themax
value.
- The current node’s value should be greater than the
-
Recursive Calls:
- Recursively check the left subtree with the updated range
[min, node->data]
. - Recursively check the right subtree with the updated range
[node->data, max]
.
- Recursively check the left subtree with the updated range
-
Return Result:
- The tree is a BST only if both left and right subtrees are BSTs.
- Expected Time Complexity:
O(N)
We visit each node exactly once, performing constant-time operations at each step. - Expected Auxiliary Space Complexity:
O(H)
Due to the recursion stack, whereH
is the height of the tree. In the worst case (skewed tree),H = N
. In the best case (balanced tree),H = log N
.
class Solution {
public:
bool isBST(Node* root, int min = INT_MIN, int max = INT_MAX) {
return !root || (root->data > min && root->data < max &&
isBST(root->left, min, root->data) &&
isBST(root->right, root->data, max));
}
};
- Perform an inorder traversal to produce a list of values.
- A BST’s inorder traversal should result in a strictly increasing sequence.
- If the sequence is not increasing, the tree is not a BST.
class Solution {
void inorder(Node* root, vector<int>& vals) {
if (!root) return;
inorder(root->left, vals);
vals.push_back(root->data);
inorder(root->right, vals);
}
public:
bool isBST(Node* root) {
vector<int> vals;
inorder(root, vals);
for (int i = 1; i < vals.size(); i++) {
if (vals[i] <= vals[i-1]) return false;
}
return true;
}
};
- Instead of recursion, use a stack to simulate inorder traversal.
- Compare each node’s value with the previous node’s value to check for the BST property.
class Solution {
public:
bool isBST(Node* root) {
stack<Node*> st;
Node* prev = nullptr;
while (root || !st.empty()) {
while (root) {
st.push(root);
root = root->left;
}
root = st.top();
st.pop();
if (prev && root->data <= prev->data) return false;
prev = root;
root = root->right;
}
return true;
}
};
Approaches | ⏱️ Time Complexity | 🗂️ Space Complexity | ⚡ Method | ✅ Pros | |
---|---|---|---|---|---|
1️⃣ Min–Max Recursion | 🟢 O(N) | 🟡 O(H) | Recursive (Min–Max) | Fastest; no extra storage | Recursive depth may cause stack overflow |
2️⃣ Inorder Traversal (Recursive) | 🟢 O(N) | 🟡 O(N) | Recursive Inorder | Simple implementation; easy to understand | Requires extra space for storing nodes |
3️⃣ Iterative Inorder Traversal | 🟢 O(N) | 🟡 O(H) | Stack-based DFS | Avoids recursion stack overflow | Code complexity is slightly higher |
-
For Balanced Trees / Small Depth:
✅ Approach 1 (Min–Max Recursion) is the fastest and most efficient. -
For Deep or Skewed Trees (Risk of Stack Overflow):
✅ Approach 3 (Iterative Inorder Traversal) handles deep recursion better. -
For Simple Understanding & Learning:
✅ Approach 2 (Inorder Traversal Recursive) is the most intuitive to grasp.
class Solution {
boolean isBST(Node root) {
return isBST(root, Integer.MIN_VALUE, Integer.MAX_VALUE);
}
boolean isBST(Node node, int min, int max) {
return node == null || (node.data > min && node.data < max &&
isBST(node.left, min, node.data) &&
isBST(node.right, node.data, max));
}
}
class Solution:
def isBST(self, root, min_val=float('-inf'), max_val=float('inf')):
return not root or (min_val < root.data < max_val and
self.isBST(root.left, min_val, root.data) and
self.isBST(root.right, root.data, max_val))
For discussions, questions, or doubts related to this solution, feel free to connect on LinkedIn: Any Questions. Let’s make this learning journey more collaborative!
⭐ If you find this helpful, please give this repository a star! ⭐