BST teksty, usuwanie przy dwóch synach

0

Witajcie mam problem z drzewem BST z tekstami,
jestem w trakcie tworzenia w funckji usuwajacej, w sytuacji gdy mamy dwóch synów.
Pomożecie?

 
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

typedef struct Node {  //mamy strukture, definicja wezla drzewa bst
  struct Node* left;   //kazdy wezel moze miec max 2je dzieci(prawe i lewe)
  struct Node* right;  //i jakas wartosc
  char *value;   // w strukturze potrzebujemy pola przechowującego tą wartosc
} Node;           //jak np. wskazniki na dzieci

Node * NewNode(const char * text){

    Node * newNode = (Node*)malloc(sizeof(Node));

    newNode->value = text;
    newNode->left = NULL;
    newNode->right = NULL;

	return newNode;
}

Node *root;

void add(const char *text)
{

    printf("Dodawanie %s\n", text);

    Node * lastNode = root;
    Node * currentNode = root;

    int b ;

    while(currentNode!=NULL){

        printf("porownywanie %s z %s\n", currentNode->value, text);

        lastNode = currentNode;

        // currentNode > text
        if (stricmp(currentNode->value,text)>0){

            b = 1;

            printf("lewo > prawo\n");

            currentNode = currentNode->left;

        }
        // currentNode < text
        else {

            b = -1;

            printf("lewo < prawo\n");

            currentNode = currentNode->right;

        }

    }

    printf("Dodawanie nowego elementu: Sukces\n\n");

    Node * newNode = NewNode(text);

    currentNode = newNode;

    if (b==1){
        lastNode->left = newNode;
    }
    else {
        lastNode->right = newNode;
    }

}
void print(Node *x)    //rekurecja
{
    if (x->left != NULL) print(x->left);
		printf("%s \n",x->value);
		if (x->right != NULL) print(x->right);

}
Node* tree_minumum(Node *x) //Funkcja pomocna przy usuwaniu elementu
{
    while(x->left!=NULL)
    {
        x=x->left;
    }
    return x;

}
void delete(const char* text)
{
    Node * currentNode = root;
    Node * lastNode = root;
    while(currentNode!=NULL)
    {

        if(stricmp(currentNode->value,text)==0)  // Jezeli znalezlismy nasz tekst do usuniecia
        {
            if((currentNode->left==NULL)&&(currentNode->right==NULL)) // Jezeli wierzcholek nie ma synow
            {
                if(stricmp(currentNode->value,lastNode->value)<0)
                   lastNode->left=NULL;
                else
                    lastNode->right=NULL;
                free(currentNode);
                        return;
            }
            if((currentNode->left==NULL)&&currentNode->right!=NULL) //Jezeli wierzcholek ma tylko prawego syna
            {
                if(stricmp(currentNode->value,lastNode->value)>0)
                    lastNode->right=currentNode->right;
                    else lastNode->left=currentNode->right;
                free(currentNode);
                return;
            }
            if((currentNode->left!=NULL)&&currentNode->right==NULL)  // Jezeli wierzcholek do usuniecia ma tylko lewego syna
            {
                if(stricmp(currentNode->value,lastNode->value)>0)
                    lastNode->right=currentNode->left;
                    else lastNode->left=currentNode->left;
                free(currentNode);
                return;
            }
            if((currentNode->left!=NULL)&&currentNode->right!=NULL) // Jezeli mamy dwoch synów
            {


            }


        }
           lastNode = currentNode;
        if (stricmp(currentNode->value,text)<0)
           {
               currentNode=currentNode->right;
           }
            else
                currentNode=currentNode->left;

    }


}

char *min()
{
    Node * currentNode = root;

    while(currentNode->left!=NULL) //schodzimy rekurencyjnie jak najbardziej w lewo
    {
        currentNode=currentNode->left;
    }

    return currentNode->value;

}
int contains(const char* text)
{
    Node * currentNode = root;
    while(currentNode!=NULL)
    {


        if(stricmp(currentNode->value,text)==0) return 1;
        if (stricmp(currentNode->value,text)<0)
           {
               currentNode=currentNode->right;
           }
            else
                currentNode=currentNode->left;

    }
    return 0;

}


int main()
{

    // rootowi trzeba nadac jakas wartosc

    root = NewNode("abx");
    add("abcd");
    //add("ad");
    //add("aas");
    //add("xaaa");
    //add("yaaa");
    //add("zzz");
   // if(contains("abc")==1) printf("Jest w drzewie \n");
printf("Metoda inorder \n");
print(root);
printf("element najmniejszy: %s\n",min());
printf("\n");
//usuwamy element i sprawdzamy czy nam sie udało
//delete("abcd");
delete("abcd");
print(root);

    return 0;

}
0

A musisz to wykonać w takiej formie? Nie łatwiej byłoby użyć tablicy i ją balansować? Zakładam, że byłoby nawet szybciej ze względu na lokalność pamięci.

0

niestety.. muszę już, mam modyfikacje do zrobienia tego programu i mnie już czas goni.. by zaliczyć ćwiczenia z programowania w c, a nie mam już głowy by pisać od nowa

0

mam jeszcze ze stronki http://www.algolist.net/Data_structures/Binary_search_tree/Removal cos takiego, ale to jest w C++ i tez nie mam wprawy jakby to przekonwertowac

bool BinarySearchTree::remove( int value ) {
   
    if( root == NULL )
   
         return false;
   
    else {
       
        if( root->getValue() == value ) {
           
            BSTNode auxRoot( 0 );
           
            auxRoot.setLeftChild( root );
           
            BSTNode * removedNode = root->remove( value, & auxRoot );
           
            root = auxRoot.getLeft();
           
            if( removedNode != NULL ) {
               
                delete removedNode;
               
                return true;
               
            } else
           
                 return false;
           
        } else {
           
            BSTNode * removedNode = root->remove( value, NULL );
           
            if( removedNode != NULL ) {
               
                delete removedNode;
               
                return true;
               
            } else
           
                 return false;
           
        }
       
    }
   
}



BSTNode * BSTNode::remove( int value, BSTNode * parent ) {
   
    if( value < this->value ) {
       
        if( left != NULL )
       
             return left->remove( value, this );
       
        else
       
             return NULL;
       
    } else if( value > this->value ) {
       
        if( right != NULL )
       
             return right->remove( value, this );
       
        else
       
             return NULL;
       
    } else {
       
        if( left != NULL && right != NULL ) {
           
            this->value = right->minValue();
           
            return right->remove( this->value, this );
           
        } else if( parent->left == this ) {
           
            parent->left =( left != NULL ) ? left
                : right;
           
            return this;
           
        } else if( parent->right == this ) {
           
            parent->right =( left != NULL ) ? left
                : right;
           
            return this;
           
        }
       
    }
   
}



int BSTNode::minValue() {
   
    if( left == NULL )
   
         return value;
   
    else
   
         return left->minValue();
   
} 

1 użytkowników online, w tym zalogowanych: 0, gości: 1