20 / \ 10 40 / \ 8 16 / 12 Figure 1Answer: The AVL condition is violated at node 20 because its two subtrees differ in height by 2. We first need to identify whether we have a zig-zig or zig-zag case. In order to make this determination we start by going to the subtree that is causing the problem. The subtree causing the problem is always the subtree with the greater height, in this case, the subtree rooted at 10. From 10 we need to determine whether the inserted key, 12, lies in 10's left or right subtree. Since 12 > 10, 12 must lie in 10's right subtree. We therefore have a zig-zag condition because we move to the left to get from 20 to 10 and then we would have to move to the right to reach 12.
Once we know that we have a zig-zag condition we can identify the node that we must rotate about. This node will be the grandchild of the node that violates the AVL condition and which lies in the direction of the inserted node. 16 is that node. In Dr. Plank's notes for the Zig-Zag case, B = 20, F = 10, and D = 16 (note that we are dealing with the symmetric case where F is a left child and D is the right child of F). Subtree A is the tree rooted at 20, subtree C is the tree rooted at 12, subtree E is empty, and subtree G is the tree rooted at 40. Using Dr Plank's Zig-Zag template and accounting for the fact that we are performing the symmetric case, we obtain:
16 / \ 10 20 / \ \ 8 12 40 Figure 2I find it hard to memorize this template so instead I like to transform the tree in two steps by first doing a left rotation about 16 that makes node 10 be a left child of 16 and then doing a right rotation about 16 that makes 20 be a right child of 16. I call this a left-right rotation or a double rotation. If I first do a left rotation about 16 I obtain:
20 / \ 16 40 / 10 / \ 8 12 Figure 3Next I do a right rotation about 16 to obtain the final tree shown in Figure 2.
Question: Suppose I change the tree in Figure 1 so that instead of inserting 12 I insert 9. Again I get an invalid AVL tree. How do I rebalance this tree?
20 / \ 10 40 / \ 8 16 \ 9 Figure 4
Answer: As in the previous case the problem node is node 20 and the problem subtree is the one rooted at node 10. However the inserted key now lies in 10's left subtree rather than 10's right subtree. Thus we now have a zig-zig case rather than a zig-zag case (we go left from 20 to 10 and then go left again if we want to get to 9). This case is easier to handle because we only have to perform a single rotation to re-balance the tree. In the left-left case that we have here we must do a single right rotation about the root of the problem subtree, which in this case is 10. The rotation will produce the following valid AVL tree:
10 / \ 8 20 \ / \ 9 16 40 Figure 5