BST中有2个孩子的删除方法,不会删除其前身

时间:2018-12-13 00:53:40

标签: recursion tree binary-tree binary-search-tree binary-search

我正在尝试为BST写一个remove方法。如果有0个或1个孩子,它会起作用。但是,如果有两个子代,则该方法会将数据从前任(最右边的左子代)复制到要删除的节点,然后应该删除前任。由于某些原因,前任者仍在树中,无法正确删除。我敢肯定这是一个简单的递归错误,但是我无法弄清楚!我将不胜感激任何帮助,反馈和意见。谢谢。

    public boolean myRemove(Object o) {
    if (isEmpty()) {
        return false;
    }
    E data = (E)o;
    root = myRemoveHelper(root, data);
    size--;
    return true;
}
private Node<E> myRemoveHelper(Node<E> root, E data) {
    if (root.data == data) {
        return myRemoveIt(root);
    }
    else if (data.compareTo(root.data) < 0) {
        root.left = myRemoveHelper(root.left, data);
    }
    else {
        root.right = myRemoveHelper(root.right, data);
    }
    return root;
}
private Node<E> myRemoveIt(Node<E> nodeToRemove) {
    if (nodeToRemove.left == null && nodeToRemove.right == null) {
        return null;
    }
    else if (nodeToRemove.left == null && nodeToRemove.right != null) {
        return nodeToRemove.right;
    }
    else if (nodeToRemove.left != null && nodeToRemove.right == null) {
        return nodeToRemove.left;
    }
    else {
        Node<E> temp = nodeToRemove.right;
        while (temp.left != null) {
            temp = temp.left;
        }
        nodeToRemove.data = temp.data;

        //does not remove the duplicate! :(
        nodeToRemove.left = myRemoveHelper(temp, temp.data);
        return nodeToRemove;
    }
}

1 个答案:

答案 0 :(得分:0)

在您说的问题中,您选择了the rightmost left child ,但是在myRemoveIt中选择了,您在以下位置转到了leftmost right child

Node<E> temp = nodeToRemove.right;
while (temp.left != null) {
    temp = temp.left;
}

但是分配到左侧后:{{​​1}}。

您需要将其更改为:

nodeToRemove.left = myRemoveHelper(temp, temp.data);

现在,您确定nodeToRemove.right = myRemoveHelper(nodeToRemove.right, temp.data); 在叶子上(或者至少我们知道他缺少左侧),并且发送到temp.data的新根是右侧,因为新数据已经存在已设置。