17-3 Amortized weight-balanced trees

Consider an ordinary binary search tree augmented by adding to each node xx the attribute x.sizex.size giving the number of keys stored in the subtree rooted at xx. Let α\alpha be a constant in the range 1/2α<11 / 2 \le \alpha < 1. We say that a given node xx is α\alpha-balanced if x.left.sizeαx.sizex.left.size \le \alpha \cdot x.size and x.right.sizeαx.sizex.right.size \le \alpha \cdot x.size. The tree as a whole is α\alpha-balanced if every node in the tree is α\alpha-balanced. The following amortized approach to maintaining weight-balanced trees was suggested by G. Varghese.

a. A 1/21 / 2-balanced tree is, in a sense, as balanced as it can be. Given a node xx in an arbitrary binary search tree, show how to rebuild the subtree rooted at xx so that it becomes 1/21 / 2-balanced. Your algorithm should run in time Θ(x.size)\Theta(x.size), and it can use O(x.size)O(x.size) auxiliary storage.

b. Show that performing a search in an nn-node α\alpha-balanced binary search tree takes O(lgn)O(\lg n) worst-case time.

For the remainder of this problem, assume that the constant α\alpha is strictly greater than 1/21 / 2. Suppose that we implement INSERT\text{INSERT} and DELETE\text{DELETE} as usual for an nn-node binary search tree, except that after every such operation, if any node in the tree is no longer α\alpha-balanced, then we "rebuild" the subtree rooted at the highest such node in the tree so that it becomes 1/21 / 2-balanced.

We shall analyze this rebuilding scheme using the potential method. For a node xx in a binary search tree TT, we define

Δ(x)=x.left.sizex.right.size,\Delta(x) = |x.left.size - x.right.size|,

and we define the potential of TT as

Φ(T)=cxT:Δ(x)2Δ(x),\Phi(T) = c \sum_{x \in T: \Delta(x) \ge 2} \Delta(x),

where cc is a sufficiently large constant that depends on α\alpha.

c. Argue that any binary search tree has nonnegative potential and that a 1/21 / 2-balanced tree has potential 00.

d. Suppose that mm units of potential can pay for rebuilding an mm-node subtree. How large must cc be in terms of α\alpha in order for it to take O(1)O(1) amortized time to rebuild a subtree that is not α\alpha-balanced?

e. Show that inserting a node into or deleting a node from an nn-node α\alpha-balanced tree costs O(lgn)O(\lg n) amortized time.

a. Since we have O(x.size)O(x.size) auxiliary space, we will take the tree rooted at xx and write down an inorder traversal of the tree into the extra space. This will only take linear time to do because it will visit each node thrice, once when passing to its left child, once when the nodes value is output and passing to the right child, and once when passing to the parent. Then, once the inorder traversal is written down, we can convert it back to a binary tree by selecting the median of the list to be the root, and recursing on the two halves of the list that remain on both sides. Since we can index into the middle element of a list in constant time, we will have the recurrence

T(n)=2T(n/2)+1,T(n) = 2T(n / 2) + 1,

which has solution that is linear. Since both trees come from the same underlying inorder traversal, the result is a BST\text{BST} since the original was. Also, since the root at each point was selected so that half the elements are larger and half the elements are smaller, it is a 1/21 / 2-balanced tree.

b. We will show by induction that any tree with αd+d\le \alpha^{-d} + d elements has a depth of at most dd. This is clearly true for d=0d = 0 because any tree with a single node has depth 00, and since α0=1\alpha^0 = 1, we have that our restriction on the number of elements requires there to only be one. Now, suppose that in some inductive step we had a contradiction, that is, some tree of depth dd that is α\alpha balanced but has more than αd\alpha - d elements.

We know that both of the subtrees are alpha balanced, and by being alpha balanced at the root, we have

root.left.sizeαroot.size,root.left.size \le \alpha \cdot root.size,

which implies

root.right.size>root.sizeαroot.size1.root.right.size > root.size - \alpha \cdot root.size - 1.

So,

root.right.size>(1α)root.size1>(1α)αd+d1=(α11)αd+1+d1αd+1+d1, \begin{aligned} root.right.size & > (1 - \alpha)root.size - 1 \\ & > (1 - \alpha)\alpha - d + d - 1 \\ & = (\alpha - 1 - 1)\alpha - d + 1 + d - 1 \\ & \ge \alpha - d + 1 + d - 1, \end{aligned}

which is a contradiction to the fact that it held for all smaller values of dd because any child of a tree of depth d has depth d1d - 1.

c. The potential function is a sum of Δ(x)\Delta(x) each of which is the absolute value of a quantity, so, since it is a sum of nonnegative values, it is nonnegative regardless of the input BST\text{BST}.

If we suppose that our tree is 1/21 / 2-balanced, then, for every node xx, we'll have that Δ(x)1\Delta(x) \le 1, so, the sum we compute to find the potential will be over no nonzero terms.

d.

c^i=ci+Φ(Di)Φ(Di1)O(1)=m+Φ(Di)Φ(Di1)Φ(Di1)=m+Φ(Di)Φ(Di1)m. \begin{aligned} \hat c_i & = c_i + \Phi(D_i) - \Phi(D_{i - 1}) \\ O(1) & = m + \Phi(D_i) - \Phi(D_{i - 1}) \\ \Phi(D_{i - 1}) & = m + \Phi(D_i) \\ \Phi(D_{i - 1}) & \ge m. \end{aligned}

Δ(x)=x.left.sizex.right.sizeαm((1α)m1)=(2α1)m+1. \begin{aligned} \Delta(x) & = x.left.size - x.right.size \\ & \ge \alpha \cdot m - ((1 - \alpha) m - 1) \\ & = (2\alpha - 1)m + 1. \end{aligned}

mc((2α1)m+1)cm(2α1)m+112α. \begin{aligned} m & \le c((2\alpha - 1)m + 1) \\ c & \ge \frac{m}{(2\alpha - 1)m + 1} \\ & \ge \frac{1}{2\alpha}. \end{aligned}

e. Suppose that our tree is α\alpha balanced. Then, we know that performing a search takes time O(lg(n))O(\lg(n)). So, we perform that search and insert the element that we need to insert or delete the element we found. Then, we may have made the tree become unbalanced. However, we know that since we only changed one position, we have only changed the Δ\Delta value for all of the parents of the node that we either inserted or deleted. Therefore, we can rebuild the balanced properties starting at the lowest such unbalanced node and working up.

Since each one only takes ammortized constant time, and there are O(lg(n))O(\lg(n)) many trees made unbalanced, tot total time to rebalanced every subtree is O(lg(n))O(\lg(n)) ammortized time.