Given a binary search tree and a node in it, find the in-order successor
of that node in the BST.
If the given node has no in-order successor in the tree, return null
Notice
It’s guaranteed p is one node in the given tree.
(You can directly compare the memory address to find p)
Example
Given tree = [2,1]
and node = 1
2
/
1
return node 2
Given tree = [2,1,3]
and node = 2
2
/ \
1 3
return node 3
我通常能直接想到的办法都是Straightforward的方法,大多数人应该也都这样。这样的方法好处是好理解,能通用;坏处是时间复杂度空间复杂度通常不是最优的。这道题我首先想到的就是先求出Binary tree inorder traversal,然后找到给出的p,返回p的下一个节点就可以了。
但我的作法并没有利用到BST的特性
//do inorder traversal of a binary search tree, and then search in the
//resultsting list
public class Solution {
public TreeNode inorderSuccessor(TreeNode root, TreeNode p) {
// write your code here
List<TreeNode> res = inorderTraversal(root);
for (int i = 0; i < res.size(); i++){
if (res.get(i) == p && i + 1 < res.size()){
return res.get(i+1);
}
}
return null;
}
private List<TreeNode> inorderTraversal(TreeNode root){
ArrayList<TreeNode> inOrder = new ArrayList<>();
if (root == null){
return inOrder;
}
TreeNode curt = root;
Stack<TreeNode> stack = new Stack<>();
while (curt != null){
stack.push(curt);
curt = curt.left;
}
while (!stack.isEmpty()){
TreeNode node = stack.pop();
inOrder.add(node);
curt = node.right;
while (curt != null){
stack.push(curt);
curt = curt.left;
}
}
return inOrder;
}
另一种解法:O(logN) 利用了BST的性质:节点左边的节点val比该节点的val小,右边的节点比该节点的val大
class Solution {
public TreeNode inorderSuccessor(TreeNode root, TreeNode p) {
if (root == null){
return null;
}
//if p has right children, its successor will be the left most node
//in its right subtree, which is also the smallest. This is due to
//the property of BST.
if (p.right != null){
return findMin(p.right);
} else {
//if current node has no right children, its successor will be one of
//its ancestors, which has the deepest depth and current node is in its
//left side.
TreeNode ancestor = root;
TreeNode successor = null;
while (ancestor != null){
//if node's val is less than ancestor, we know node is in the left
//side of ancestor. But we are not sure if it is the closet to node,
//or in other words the one has the deepest depth, so we move
//left to update ancestor.
if (p.val < ancestor.val){
successor = ancestor;
ancestor = ancestor.left;
} else {
//if node's val is larger than ancestor, we know that node is
//in the right side of ancestor. So we move ancestor to the right
ancestor = ancestor.right;
}
}
return successor;
}
}
private TreeNode findMin(TreeNode root){
if (root == null){
return null;
}
while (root.left != null){
root = root.left;
}
return root;
}
}
helpful resources
Inorder Successor in a binary search tree