## # 99. Recover Binary Search Tree

Two elements of a binary search tree (BST) are swapped by mistake.

Recover the tree without changing its structure.

Example 1:

``````Input: [1,3,null,null,2]

1
/
3
\
2

Output: [3,1,null,null,2]

3
/
1
\
2
``````

Example 2:

``````Input: [3,1,4,null,null,2]

3
/ \
1   4
/
2

Output: [2,1,4,null,null,3]

2
/ \
1   4
/
3
``````

• A solution using O(n) space is pretty straight forward.
• Could you devise a constant space solution?

### # Solution

Approach 1: run an inorder traversal, record all values then sort them -- compare with the unsorted. Time: O(NlogN) -- sorting. Space: O(N) -- the table, inorder values, and sorted inorder values.

Approach 2: do an inorder traversal; if we can find 1 single reversed value, then the swapped nodes are the reversed and the one right after it; if we can find 2 reversed values, then the first swapped is the node before the reversed, and the second swapped is the node reversed. Time: O(N), space: O(1).

Approach 3: run an inorder traversal and record the two swapped nodes.

### # Code (Python)

Approach 1:

``````    def recoverTree(self, root: 'TreeNode') -> 'None':
"""
Do not return anything, modify root in-place instead.
"""
val_to_node = {}
inorder = []
node = root
stack = []
while node:
stack.append(node)
node = node.left
while stack:
node = stack.pop()
val_to_node[node.val] = node
inorder.append(node.val)
if node.right:
node = node.right
while node:
stack.append(node)
node = node.left
inorder_sorted = list(sorted(inorder))
for i in range(len(inorder)):
if inorder[i] != inorder_sorted[i]:
node1, node2 = val_to_node[inorder[i]], val_to_node[inorder_sorted[i]]
node1.val, node2.val = node2.val, node1.val
break
``````

Approach 2:

``````    def recoverTree(self, root):
swapped = [None, None]
prev_node = None
# Morrison's inorder traversal with O(1) space
node = root
while node:
if not node.left:
# visit node
if prev_node and node.val < prev_node.val:
if not swapped:
swapped = prev_node
swapped = node
else:
swapped = node
prev_node = node
node = node.right
else:
predecessor = node.left
while predecessor.right and predecessor.right != node:
predecessor = predecessor.right
if not predecessor.right:
predecessor.right = node
node = node.left
else:
predecessor.right = None
# visit node
if prev_node and node.val < prev_node.val:
if not swapped:
swapped = prev_node
swapped = node
else:
swapped = node
prev_node = node
node = node.right
swapped.val, swapped.val = swapped.val, swapped.val
``````

### # Code (C++)

Approach 3:

``````/**
* Definition for a binary tree node.
* struct TreeNode {
*     int val;
*     TreeNode *left;
*     TreeNode *right;
*     TreeNode(int x) : val(x), left(NULL), right(NULL) {}
* };
*/
class Solution {
private:
TreeNode *prev;
TreeNode *swap1;
TreeNode *swap2;
void doRecoverTree(TreeNode* root) {
if (root == NULL)
return;
doRecoverTree(root->left);
if (prev && prev->val > root->val)
{
if (swap1 == NULL)
{
swap1 = prev;
swap2 = root;
}
else
{
swap2 = root;
}
}
prev = root;
doRecoverTree(root->right);
}
public:
void recoverTree(TreeNode* root) {
prev = NULL;
swap1 = NULL;
swap2 = NULL;
doRecoverTree(root);
if (swap1 && swap2)
std::swap(swap1->val, swap2->val);
}
};
``````