2016-09-12 2 views
0

Ich versuche, eine verknüpfte Liste zu erstellen, aber ich habe Probleme, weil ich meine Knoten zweimal lösche. Das Problem tritt nur dann auf, wenn ein Knoten in eine Funktion übergeben wird (wenn er als Referenz übergeben wird, ist alles in Ordnung), was zu der Annahme führt, dass das in die Funktion übergebene Objekt so kopiert wird, dass die Zeiger auf Knoten zeigen von der ursprünglichen Liste nicht die neue Liste. Ich habe versucht, dies zu umgehen, indem ich den = Operator überbelastete, aber das hat auch nicht funktioniert. Eine Erklärung dessen, was ich falsch mache, wäre großartig.C++ verknüpfte Liste funktioniert nicht

Danke für die Hilfe

#include <iostream> 

struct node{ 
    node(int n){ 
     if (n == 1){ 
      data = 1; 
      next = NULL; 
     } 
     if (n == 2){ 
      data = 2; 
      next = new node(1); 
      next -> next = NULL; 
     } 
    } 
    ~node(){ 
     std::cout << data << std::endl; 
     if (next != NULL) delete next; 
    } 

    void operator=(node a){ 
     next = NULL; 
    } 

    int data; 
    node* next; 
}; 

void func2(node v){ 
} 


int main(){ 

    node v(2); 
    if (v.next -> next == NULL) std::cout << "true\n"; 
    func2(v); 

    return 0; 
} 

Antwort

3

Ihr Verdacht richtig ist, aber darin liegt das Problem; Wenn Sie den Knoten in func2 übergeben, kopieren Sie nur den ersten Knoten, nicht die gesamte Liste. Der Kopierkonstruktor kopiert den ersten Knoten und den Zeiger im ersten Knoten (der auf den ursprünglichen zweiten Knoten verweist). Wenn v den Gültigkeitsbereich in func2 verlässt, wird er einmal gelöscht und dann wieder gelöscht, wenn er den Gültigkeitsbereich verlässt von main. Sie müssen den Kopierkonstruktor schreiben, um eine "tiefe Kopie" zu erstellen, indem Sie die gesamte Liste durchlaufen und jeden Knoten an eine neue Adresse kopieren.

Denken Sie auch daran, dass der Kopierkonstruktor in den meisten Fällen *this zurückgeben sollte, dies ist in den C++ - FAQ und im Buch "Effective C++" von Scott Meyers. So sollte die Unterschrift sein:

node& operator=(const node& node); 

Wenn Sie den Zuweisungsoperator zu überlasten sind, sollten Sie wahrscheinlich auch eine Kopie Konstruktor definieren. Gute Arbeit, das Problem übrigens zu erklären.

Edit: Der Code würde so aussehen. Ich entschuldige mich, dass ich das nicht getestet habe; Ich bin auf meinem Tablet und die Bearbeitung ist schmerzhaft ...

#include <iostream> 

struct node{ 
    node(const node& toCopy) : data(toCopy.data) 
    { 
     if(toCopy.next != null) { 
      next = new node(toCopy); 
     } 
    } 

    node(int n){ 
     if (n == 1){ 
      data = 1; 
      next = NULL; 
     } 
     if (n == 2){ 
      data = 2; 
      next = new node(1); 
      next -> next = NULL; 
     } 
    } 

    node& operator=(const node& toCopy) { 
     if(&toCopy != this) { 
      data = toCopy.data; 

      if(next != NULL) { 
       next = new node(toCopy); 
      } 
     } 

     return *this; 
    } 

    ~node(){ 
     std::cout << data << std::endl; 
     if (next != NULL) delete next; 
    } 

    int data; 
    node* next; 
}; 

void func2(node v){ 
} 


int main(){ 
    node v(2); 
    if (v.next -> next == NULL) std::cout << "true\n"; 
    func2(v); 

    return 0; 
} 
+0

Danke für die Antwort. Wenn du erklären könntest, wie ich das beheben würde, wäre das großartig. Mir ist nicht klar, warum mein Operator = Überladung nicht funktioniert und das Problem alleine löst. – fred