Jak przekonwertować binarne drzewo binarne drzewo poszukiwań w miejscu, to znaczy, nie możemy użyć dowolnego dodatkowego miejsca

głosy
12

Jak przekonwertować binarne drzewo do drzewa binarnego wyszukiwania w miejscu, to znaczy, że nie można korzystać z dodatkowej przestrzeni.

Utwórz 05/04/2010 o 06:46
źródło użytkownik
W innych językach...                            


10 odpowiedzi

głosy
0

Binarne drzewo zwykle jest wyszukiwanie binarne drzewo, w takim przypadku nie jest wymagana żadna konwersja.

Być może trzeba wyjaśnić strukturę czego konwersji z. Czy drzewo źródło niezrównoważony? Czy to nie uporządkowane według klucza, który chcesz wyszukiwać? Skąd przybywamy na drzewie źródłowym?

Odpowiedział 05/04/2010 o 07:00
źródło użytkownik

głosy
0

Dobrze, jeśli jest to pytanie wywiad, pierwszą rzeczą, którą bym wygadać (z zerowym rzeczywistej myśli) to: iteracyjne całą binarnego rekurencyjnie i i znaleźć najmniejszy element. Wyjąć ją z drzewa binarnego. Teraz powtórzyć proces, w którym iteracyjne całe drzewo i znaleźć najmniejszy element i dodać go jako rodzic ostatniego elementu znalezionego (z poprzedniego elementu coraz lewy dziecko nowego węzła). Powtarzać tyle razy, ile to konieczne, dopóki oryginalne drzewo jest pusty. Na koniec pozostaje ci najgorszym możliwym posortowanej binarne drzewo - połączonej listy. Wskaźnik jest skierowany do węzła głównego, który jest największym elementem.

To jest straszne algorytm wszystko wokół - O (n ^ 2) Czas pracy z najgorszym możliwym wyjście binarne drzewa, ale to przyzwoity punkt wyjścia przed wymyślanie czegoś lepszego i ma tę zaletę, że jesteś w stanie napisać kod to około 20 linii na tablicy.

Odpowiedział 05/04/2010 o 07:50
źródło użytkownik

głosy
10

Nie dać dużo, aby przejść dalej, ale jeśli wymogiem jest to, co myślę, że jest, masz binarne drzewo już stworzony i siedzi w pamięci, ale nie klasyfikowane (tak, jak ma to być sortowane, w każdym razie).

Jestem przy założeniu, że węzły drzewa wyglądają jak

struct tree_node {
    struct tree_node * left;
    struct tree_node * right;
    data_t data;
};

Jestem również przy założeniu, że można czytać C

Chociaż moglibyśmy usiąść zastanawiając się, dlaczego to drzewo zostało kiedykolwiek stworzono bez zostały stworzone w celu segregowanych, że nie robi nam nic dobrego, więc będę ją zignorować i po prostu do czynienia z sortowania go.

Wymóg, aby być stosowany bez dodatkowej przestrzeni jest nieparzysta. Chwilowo nie będzie dodatkowe miejsce, jeśli tylko na stosie. Mam zamiar założyć, że oznacza to, że wywołanie malloc czy coś takiego, a także, że otrzymany drzewo ma używać nie więcej pamięci niż oryginalny niesegregowanych drzewa.

Pierwszym i najprostszym rozwiązaniem jest zrobić preorder przechodzenie z niesegregowanych usuwania każdy węzeł drzewa z tego drzewa i robi posortowaną wprowadzenie do nowego drzewa. Jest to O (n + n log (n)), co O (N log (n)).

Jeśli nie jest to, czego chcą i masz zamiar użyć obroty i rzeczy ..... to jest straszne!

Pomyślałem, że można to zrobić wykonując dziwne wersję sterty sortowania, ale wpadłem na problemy. Inną rzeczą, która przyszła mi do głowy, co byłoby potwornie powolne, by zrobić dziwną wersję sortowanie bąbelkowe na drzewie.

W tym celu każdy węzeł jest porównywany i ewentualnie zamienione ze sobą na jego bezpośrednie dzieci (a więc także z jego rodzica), aż Ci przemierzać drzewa i nie znaleźliśmy żadnych potrzebnych swapy. Robi shaker sortowania (sortowanie bąbelkowe, że idzie od lewej do prawej i od prawej do lewej) wersja to będzie działać najlepiej, a po pierwszym przejściu nie musiałby przechodzić w dół poddrzewa, które nie wyglądają w porządku w stosunku do jego rodzic ,

Jestem pewien, że albo ten algorthm została wymyślona przez kogoś innego przed sobą i ma fajną nazwę, ja po prostu nie wiem, czy to, że jest wadliwy w jakiś sposób, że nie widzę.

Wymyślanie obliczeń run-czas na drugą sugestia jest dość skomplikowana. Na początku myślałem, że to po prostu oznaczać O (n ^ 2), jak bańki i wytrząsania rodzaju, ale nie mogę zadowolić się, że unikanie subtree przejścia nie może wygrać wystarczy, aby uczynić go trochę lepiej niż O (n ^ 2). Zasadniczo Bubble shaker sortuje się tej optymalizacji też, ale tylko na końcach których występuje całkowity posortowania wcześnie i można ściąć granice. W tej wersji drzewa masz oppurtunities aby ewentualnie uniknąć kawałki w środku zbioru, jak również. Cóż, jak już mówiłem, to prawdopodobnie śmiertelnie błędna.

Odpowiedział 05/04/2010 o 08:09
źródło użytkownik

głosy
-1

Czy Inorder przechodzenie drzewa binarnego i zapisać wynik. posortować wyniki w porządku uformować przeszukiwania binarnego drzewa za sobą środkowy element listy posortowanej jako root acending (można to zrobić za pomocą wyszukiwania binarnego). więc uzyskać zrównoważoną wyszukiwania binarne drzewo.

Odpowiedział 15/12/2010 o 05:12
źródło użytkownik

głosy
1

Czy następujący algorytm do osiągnięcia rozwiązania.

1) znaleźć w kolejności następca bez użycia jakiegokolwiek miejsca.

Node InOrderSuccessor(Node node)
{ 
    if (node.right() != null) 
    { 
        node = node.right() 
        while (node.left() != null)  
            node = node.left() 
        return node 
    }
    else
    { 
        parent = node.getParent(); 
        while (parent != null && parent.right() == node)
       { 
            node = parent 
            parent = node.getParent() 
        } 
        return parent 
    } 
} 

2) Czy w celu przechodzenia bez wykorzystania przestrzeni.

a) Znajdź pierwszy węzeł Inorder przechodzenia. Należy lewo najwięcej dziecko drzewa, jeśli ma, lub w lewo od pierwszego prawego dziecka, jeśli ma, lub samo prawo dziecka. b) Za pomocą powyższego algorytmu do znalezienia inoder następcy pierwszego węzła. c) Powtórzyć etap 2 na całej zwróconej następcy.

Użyj powyżej 2 algorytmu i wykonać w celu przechodzenia na drzewie binarnym bez zajmowania dodatkowego miejsca. Tworzą przeszukiwania binarnego drzewa robiąc przechodzenie. Ale złożoność jest O(N2)najgorszy przypadek.

Odpowiedział 15/12/2010 o 05:35
źródło użytkownik

głosy
-1

heap sort drzewie .. nlogn złożoność ..

Odpowiedział 13/06/2011 o 20:23
źródło użytkownik

głosy
2

Wykonaj PostOrder Traversal i od tego utworzyć binarne drzewo poszukiwań.

struct Node * newroot = '\0';

struct Node* PostOrder(Struct Node* root)
{
      if(root != '\0')
      {
          PostOrder(root->left);
          PostOrder(root->right);
          insertBST(root, &newroot);
      }
}

insertBST(struct Node* node, struct Node** root)
{
   struct Node * temp, *temp1;
   if( root == '\0')
   {
      *root == node;
       node->left ==  '\0';
       node->right == '\0';
   }
   else
   {
       temp = *root;
       while( temp != '\0')
       {
           temp1= temp;
           if( temp->data > node->data)
               temp = temp->left;
           else
               temp = temp->right;
       }
       if(temp1->data > node->data)
       {
           temp1->left = node;
       }
       else
       {
           temp1->right = node;
       }
       node->left = node->right = '\0';
    }
}
Odpowiedział 10/01/2012 o 05:27
źródło użytkownik

głosy
14

Konwersja binarne drzewo do podwójnie połączonej listy- można zrobić inplace w O (n)
Następnie sortowania go przy użyciu scalania sortowania nlogn
Konwersja listy z powrotem do drzewa - O (n)

Proste nlogn rozwiązanie.

Odpowiedział 29/08/2012 o 15:37
źródło użytkownik

głosy
0
#include <stdio.h>
#include <stdlib.h>

typedef int data_t;

struct tree_node {
    struct tree_node * left;
    struct tree_node * right;
    data_t data;
};

        /* a bonsai-tree for testing */
struct tree_node nodes[10] =
{{ nodes+1, nodes+2, 1}
,{ nodes+3, nodes+4, 2}
,{ nodes+5, nodes+6, 3}
,{ nodes+7, nodes+8, 4}
,{ nodes+9, NULL, 5}
,{ NULL, NULL, 6}
,{ NULL, NULL, 7}
,{ NULL, NULL, 8}
,{ NULL, NULL, 9}
        };

struct tree_node * harvest(struct tree_node **hnd)
{
struct tree_node *ret;

while (ret = *hnd) {
        if (!ret->left && !ret->right) {
                *hnd = NULL;
                return ret;
                }
        if (!ret->left ) {
                *hnd = ret->right;
                ret->right = NULL;;
                return ret;
                }
        if (!ret->right) {
                *hnd = ret->left;
                ret->left = NULL;;
                return ret;
                }
        hnd = (rand() &1) ? &ret->left : &ret->right;
        }

return NULL;
}

void insert(struct tree_node **hnd, struct tree_node *this)
{
struct tree_node *ret;

while ((ret= *hnd)) {
        hnd = (this->data  < ret->data ) ? &ret->left : &ret->right;
        }
*hnd = this;
}

void show(struct tree_node *ptr, int indent)
{
if (!ptr) { printf("Null\n"); return; }

printf("Node(%d):\n", ptr->data);
printf("%*c=", indent, 'L');  show (ptr->left, indent+2);
printf("%*c=", indent, 'R');  show (ptr->right, indent+2);
}

int main(void)
{
struct tree_node *root, *this, *new=NULL;

for (root = &nodes[0]; this = harvest (&root);  ) {
        insert (&new, this);
        }

show (new, 0);
return 0;
}
Odpowiedział 24/12/2012 o 00:49
źródło użytkownik

głosy
0
struct Node
{
    int value;
    Node* left;
    Node* right;
};

void swap(int& l, int& r)
{
    int t = l;
    l = r;
    r = t;
}

void ConvertToBST(Node* n, Node** max)
{
    if (!n) return;

    // leaf node
    if (!n->left && !n->right)
    {
        *max = n;
        return;
    }

    Node *lmax = NULL, *rmax = NULL;
    ConvertToBST(n->left, &lmax);
    ConvertToBST(n->right, &rmax);

    bool swapped = false;
    if (lmax && n->value < lmax->value)
    {
        swap(n->value, lmax->value);
        swapped = true;
    }

    if (rmax && n->value > rmax->value)
    {
        swap(n->value, n->right->value);
        swapped = true;
    }

    *max = n;
    if (rmax && rmax->value > n->value) *max = rmax;

    // If either the left subtree or the right subtree has changed, convert the tree to BST again
    if (swapped) ConvertToBST(n, max);
}
Odpowiedział 14/09/2013 o 07:56
źródło użytkownik

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more