2016-04-07 51 views
1

Aşağıdaki naif kod, ana işlevdeki tüm öğeleri yazdırmadan bağlantılı bir liste uygular, her şey iyi olur. Bununla birlikte, LinkedList::printll işlevi ayarlanmış bir hatayı (Gcc 5.3.0) tetikleyecektir, sorun, kafa düğümünün uygun şekilde ele alınmasıyla ilgilidir.Bağlantılı listede baş düğüm

Bu kodun çalışması için herhangi bir yol var mı? printll işlevinin en az modifikasyonu?

#include <iostream> 

using namespace std; 

struct Node{ 
    int value; 
    Node* next; 
}; 

struct LinkedList{ 
    Node* head= NULL ; 
    void append(int); 
    void printll(); 
}; 

void LinkedList::append(int data){ 
    Node* cur = head; 
    Node* tmp = new Node; 
    tmp->value = data; 
    tmp->next = NULL; 

    if(!cur){ 
     cur = tmp;      // cur-> head 
    } 
    else{ 
     while(cur->next != NULL){ 
     cur = cur->next; 
     } 
     cur->next = tmp; 
    } 
    std::cout<<cur->value<<std::endl; // cur-> temp 
    delete tmp;       // comment out 
} 

void LinkedList::printll(){ 
    Node* cur = head; 
     while(cur->next != NULL){  // 
     std::cout<<cur->value<<std::endl; 
     cur = cur->next; 
     } 
} 


int main(){ 
    LinkedList LL; 
    LL.append(5); 
    LL.append(6); 
    LL.append(7); 
    LL.printll(); // --without this, the program is fine 
    return 0; 
} 

cevap

3

Sen append bazı hatalar: Yerel kopyasına

if(!cur){ 
    cur = tmp; 
} 

Bu yalnızca atar. Burada head'u ayarlamaya çalıştığınızı varsayalım, yani şunu yapın: head = tmp;. Bu durumda, ayarlamadığınız için cur yazdıramayacağınızı unutmayın. Ancak tmp->value'u yazdırabilirsiniz. Sonra

:

delete tmp; 

Sadece az oluşturulduğu ve yerine atanan - neden bunu siliyorsunuz? numaralı telefonu, numaralı telefon hattına hala bir işaretçi olduğunu biliyorsunuz. İşiniz bittiğinde listeyi temizlediğinizde (sadece şu anda yapmadığınız) sadece delete.

A -> B -> C -> NULL 

Bu düğüm C üzerinde durur, ama asla C 'ın değerini yazdırmak: duracaktır zaman düşünmek - Bunun dışında

, sizin printll son öğe yazdırmaz. Sadece değiştirebilirsiniz:

while(cur->next != NULL){ 

while(cur != nullptr){ 

(Ayrıca, ben endl sevmiyorum)

ile.

See here for these changes running

:

#include <iostream> 

struct Node{ 
    int value; 
    Node* next; 
}; 

struct LinkedList{ 
    Node* head = nullptr ; 
    void append(int); 
    void printll(); 
}; 

void LinkedList::append(int data){ 
    Node* cur = head; 
    Node* tmp = new Node; 
    tmp->value = data; 
    tmp->next = nullptr; 

    if(!cur){ 
     head = tmp; 
    } 
    else{ 
     while(cur->next != nullptr){ 
      cur = cur->next; 
     } 
     cur->next = tmp; 
    } 
} 

void LinkedList::printll(){ 
    Node* cur = head; 
    while(cur != nullptr){ 
     std::cout << cur->value << '\n'; 
     cur = cur->next; 
    } 
} 


int main(){ 
    LinkedList LL; 
    LL.append(5); 
    LL.append(6); 
    LL.append(7); 
    LL.printll(); 
} 
+0

@BoBTFish söylediği gibi sen tmp silmek 'kaldırması gerekir;' koddan ('a' node' Yeni ilave delete' neden 'List'? 've 'printll' içinde' while' döngüsünü değiştirin, öneri: 'while (cur)' –

+0

@BoBTFish tarafından önerilen tüm değişti ve derlemek için GCC 5.3.0 kullanıyorum, ancak , hala segfault .. problem "cur-> next" de meydana geliyor sanırım – lorniper

+0

@lorniper Ben önerdiğim değişiklikleri yaptım, düzgün bir şekilde derleyebildim ve çalıştırabiliyordum. Hala segfaulting olan tam kodunuzu gönderebilir misiniz? – BoBTFish

0

1.you Cann't

delete tmp; 

nedeni tmp Eğer tmp silmek çalıştırdığınızda, nesneyi silmek, göstericisidir.

2.The baskı fonksiyonu böyle olmalıdır:

void LinkedList::printll(){ 
    Node* cur = head; 
     while(cur->next != NULL){  // -> problems is here 
     std::cout<<cur->value<<std::endl; 
     cur = cur->next; 
     } 
     std::cout<<cur->value<<std::endl; 
}