2015-05-23 2 views
1

Мой код вставки элементов в бинарном дереве поиска, но после вставки первого элемента программа прекратит работу и не выполняет дальнейшихОшибка при вставке в бинарном дереве поиска

typedef struct BST 
{ 
    int info; 
    struct BST * left; 
    struct BST *right; 
} 
bst; 

// Глобальная переменная корень

bst *root; 

// Вставить функцию

void insert(int x) //x is the elemnent to be inserted 
{ 
bst *ptr,*ptr1; 
ptr=(bst*)malloc(sizeof(bst)); 
if(root==NULL) //checking whether the tree is empty or not 
    { 
    ptr->left=ptr->right=NULL; 
    root=ptr; 
    } 
else 
    { 
    ptr1=root; 
while(ptr1!=NULL) 
    { 
    if(x>ptr1->info) //traversing to right if element is greater than element present 
    ptr1=ptr1->right; 
    else 
    ptr1=ptr1->left; //traversing to left if element is present than the the element 
    } 
} 
if(x>ptr1->info) 
{ 
    ptr1->right=ptr; 
    ptr->info=x; 
} 
else 
{ 
    ptr1->left=ptr; 
    ptr->info=x; 
} 
} 

// показать функции с помощью обхода

void preorder(bst *root) 
{ 
bst *ptr=root; 
printf("%d",ptr->info); 
preorder(ptr->left); 
preorder(ptr->right); 
} 

int main() 
{ 
int n,x,i; 
puts("Enter number of elements"); 
scanf("%d",&n); 
for(i=0;i<n;i++) 
    { 
    puts("Enter elements"); 
    scanf("%d",&x); 
    insert(x); 
} 
preorder(root); 
return 0; 
} 
+0

Добавить свой основной код функции. Еще лучше, не разделяйте ничего, если весь ваш код намного дольше, чем то, что уже опубликовано. Боковое примечание: ваша функция 'preorder' не очень, если что-то есть' NULL' -> Это определенно не сработает. – Amit

+0

Ваш код обхода проверяет, является ли ptr1 NULL, но затем он обращается к ptr1-> right и ptr1-> слева, не проверяя сначала, если они не являются NULL. – OrenD

ответ

1

В вашем случае вам нужен узел, под которым должен быть вставлен новый узел. В вашем случае, когда вы проверяете на том месте, где новый узел должен быть вставлен:

while(ptr1!=NULL) 
    { 
    if(x>ptr1->info) //traversing to right if element is greater than element present 
    ptr1=ptr1->right; 
    else 
    ptr1=ptr1->left; //traversing to left if element is present than the the element 
    } 

Вы можете сохранить предыдущий указатель, а затем использовать его на последующих стадиях.

ptr1= root; 
prev_ptr = NULL; 
while(ptr1!=NULL) 
     { 
     prev_ptr = ptr; 
     if(x>ptr1->info) //traversing to right if element is greater than element present 
     ptr1=ptr1->right; 
     else 
     ptr1=ptr1->left; //traversing to left if element is present than the the element 
     } 

Теперь используйте prev_ptr в следующем коде, который у вас есть.

+0

Я не могу понять, почему я должен это делать – codebie

+0

Скажите, что у вас есть дерево с последовательностью вставки 4,3,7,6 И вы пытаетесь вставить 5. Затем ваш ptr1 будет пересекать дерево в следующем порядке: > 7-> 6, at 6, ptr1 все еще не NULL и, следовательно, продолжит цикл while, и там будет выполнено условие else, и вы назначите 'ptr1 = ptr1-> left', который сделает' ptr1'', NULL' и, следовательно, выйти из цикла while. Но вам нужно было сделать 5 дочерним по 6, для чего вам понадобился указатель на узел 6. Именно по этой причине вам нужно 'prev_ptr' – user2959757

+0

Я не получаю вас – codebie

Смежные вопросы