Binary Search Tree Deletion (Inorder Pred method) C++

…衆ロ難τιáo~ 提交于 2019-12-24 10:24:34

问题


Ok so I thought it was fixed, but I'm getting totally inconsistent results. I rewrote it kind of from scratch to start fresh and here are my results. I get no errors, no crashing, it just doesn't remove them. It just totally messes up the tree and gives me a ton more leaves, and mixes everything up. Not sure where else to go

template <class T>
void BST<T>::remove(struct Node<T>*& root, const T& x)
{
   Node<T>* ptr = root;
   bool found = false;
   Node<T>* parent;


   while (ptr != NULL && !found)
   {
       if (x < ptr->data)
       {
           parent = ptr;
           ptr = ptr->left;
       }
       else if (x > ptr->data)
       {
           parent = ptr;
           ptr = ptr->right;
       }
       else
           found = true;
   }

   if (found == false)
       return;
   else
   {
       if(ptr->left != NULL && ptr->right != NULL)
       {
           Node<T>* inOrderPtr = ptr->left;
           parent = ptr;
           while (inOrderPtr->right != NULL)
           {
               parent = inOrderPtr;
               inOrderPtr = inOrderPtr->right;
           }

           ptr->data = inOrderPtr->data;
           ptr = inOrderPtr;
       }
    Node<T>* subPtr = ptr->left;
    if (subPtr == NULL)
        subPtr = ptr->right;

    else if (parent->left == ptr)
        parent->left = subPtr;

    else
        parent->right = subPtr;

    delete ptr;
    }

回答1:


Are each T found in the tree unique? It looks like they are from your code...

It looks like this should work:

In the else case deleting the root node:

Node<T> *tmp_r = root->left;
Node<T> *parent = root;
while (tmp_r->right != NULL)
{
    parent = tmp_r;
    tmp_r = tmp_r->right;
}
Node<T> *tmp_l = tmp_r;
while (tmp_l->left != NULL)
    tmp_l = tmp_l->left;

tmp_l->left = root->left;
tmp_r->right = root->right;
parent->right = NULL;

parent = root;
root = tmp_r;
delete parent;



回答2:


What actually was happening is that might searches were reversed so it would actually just keep going right but the data wasn't really matching correctly and so it would hit a wall it seems.

if (root->data < x)
        remove(root->left, x);
    else 
        remove(root->right, x);

should have been

if(x < root->data)
remove(root->left, x);
else
remove(root->right, x);



回答3:


You shouldn't be calling remove() recursively in the third case (where your "not sure if this is right" comment is). In the case where the the node to remove has two children, what you want to do is find the right-most child of the left child (as you are doing; the resulting node is stored in parent). This node has no right child - make it so that its right child is the right child of the node to be deleted. Then just change the root variable to be its left child; no need to change the data member in any nodes or to call remove recursively.

In pictures:

Before:
         r  <- root points here
       /  \
      /    \
     a      b
    / \    / \
   x   c  y   y
      / \
     x   d
        /
       x

After:
      a    <-- root points here
     / \
    x   c
       / \
      x   d
         / \
        x   b
           / \
          y   y


来源:https://stackoverflow.com/questions/245838/binary-search-tree-deletion-inorder-pred-method-c

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!