2

The code I have is

private Node rotateLeftChild(Node n)
{
    Node o = n.left;
    n.left = o.right;
    o.right = n;
    return o;
}

When I call it to rotate a tree like this at the root:

             7
            / \
           4   8
          / \   
         1   5

it deletes the 4 and 1 and makes 5 the left root of 7. I tried just making the method a void method but that doesn't seem to work either. Am I going at this the completely wrong way?

Pat Gallagher
  • 83
  • 2
  • 10
  • By "rotate", do you mean swapping `4` and `8` relative to `7` (ie swapping `left` and `right`)? –  Nov 30 '12 at 05:43
  • 1
    Have you tried to debug? I would put a break-point at *return o* to check. I don't think there's an issue with your left rotation code though, the problem might be somewhere higher up (*maybe where you're trying to use your rotation code*) – Sujay Nov 30 '12 at 05:48
  • This is a supporting method, but right now it isn't working when I just use it by itself. – Pat Gallagher Nov 30 '12 at 05:49
  • In this case I'm trying to make 4 the root and 7 it's right Node. – Pat Gallagher Nov 30 '12 at 05:51
  • Hey, everything is alright, your code is totally wrong. Explanation: parent of 7 still contains link to a 7. – Viktor Lova Nov 30 '12 at 18:55

1 Answers1

2

As first, sorry for my English.

Answer to a question - why node 4 dissapears is simple. 7 have parent node (or 7 is root). When you call rotateLeftChild, parent of 7 still "thinking" that his child is 7, not 4:

Real picture

So, there are tree solutions:

  1. Make link to a parent node and update it. In the end of leftRotation, make assignment, n.Parent.Left = o or n.Parent.Right = o (if (n.Parent.Left == n) or (n.Parent.Right == n) respectively). Of course, you must update links to tree's root, when you rotate child of root.

  2. When you are adding | inserting | finding node, save all previous (parent) nodes in stack, and then after rotation you must update links to their children. Or use recursion like this:

    private Splay(Node parent, Node cur, Node n, bool canMoveUpTwice = false) {
        if (cur.Value > n.Value)
            Splay(cur, cur.Left, n, !canMoveUpTwice);
        else
            Splay(cur, cur.Right, n, !canMoveUpTwice);
    
        if (canMoveUpTwice)
            MoveUpTwice();
        else
            MoveUpOnce();
    
        if (parent.Left == cur)
            parent.Left = n;
        else
            parent.Right = n;
    
        if (Parent == null)
            tree.Root = n;
    }
    

    How to use. After adding node, you must run Splay(root, newNode). Be sure, you'll get stack overflow.

  3. You must swap values of nodes and then think that nodes have been swapped. In standart implementation of rotation we have such picture: Simple rotations In rotation with swaps we get this (=x means "node have value X"): Rotations by swap So, we have this code

    private rotateLeftChild(Node q) {
        Node p = q.Left;
    
        Swap(q.Value, p.Value); 
    
        A = p.Left;
        B = p.Right;
        C = q.Right;
    
        q.Left  = A;
        q.Right = p;
    
        p.Left  = B;
        p.Right = C;
    }
    

Be careful: the code has not been tested.

Community
  • 1
  • 1
Viktor Lova
  • 4,776
  • 2
  • 19
  • 25