private TreeNode balance(TreeNode node) {
        if (node == null) {
            return null;
        }

        if (height(node.node1) - height(node.node2) >= 2) {
            if (height(node.node1.node1) > height(node.node1.node2)) {
                node = rotateLToR(node);
            }
            else if (height(node.node1.node2) > height (node.node1.node1)) {
                node = doubleL(node);
            }
        }
        else if (height(node.node2) - height(node.node1) >= 2) {
            if (height(node.node2.node2) > height(node.node2.node1)) {
                node = rotateRToL(node);
            }
            else if (height(node.node2.node1) > height(node.node2.node2)) {
                node = doubleR(node);
            }
        }

        node.height = Math.max(height(node.node1), height(node.node2)) + 1;

        return node;
    }