2017-10-19 19 views
1

On me dit que cela échouera à ajouter correctement le nœud à la liste, mais je l'ai testé et il semble fonctionner. Quelqu'un peut-il me faire savoir ce qui est incorrect dans ce code?Code pour ajouter un élément au début d'une liste dans c - quelle est l'erreur?

struct node { 
    int num; 
    struct node* next; 
}; 

void add_first(struct node* head, struct node* new_node) { 
    new_node->next = head; 
    head = new_node; 
} 

La question exacte que je suis en train de répondre est:

a) Cette fonction ne pas donner le résultat escompté (à savoir, ajouter le nœud). Quel est le problème et quand cela se produit-il? Pour tenter de trouver le problème, j'ai créé quatre noeuds, utilisé la fonction add_first et affiché les résultats. J'ai l'impression d'obtenir une sortie correcte, cependant. Voici le programme que j'ai écrit, non compris dans l'ensemble les fonctions ci-dessus:

void display(struct node* head) { 
    printf("%d ", head->num); 
    if(head->next == NULL) { 
     return; 
    } 
    display(head->next); 
} 

int main() { 
    struct node* n1; 
    struct node* n2; 
    struct node* n3; 

    n1 = (struct node*)malloc(sizeof(struct node*)); 
    n2 = (struct node*)malloc(sizeof(struct node*)); 
    n3 = (struct node*)malloc(sizeof(struct node*)); 

    n1->num = 1; 
    n2->num = 2; 
    n3->num = 3; 

    add_first(n1, n2); 
    add_first(n2, n3); 

    display(n3); 

    return 0; 
} 

La sortie Je reçois est:

Ce qui semble être correct. Donc, si j'obtiens la sortie correcte, pourquoi la fonction échoue-t-elle à donner le résultat attendu? Je n'y vois pas de problème.

+0

Le problème le plus important est que vous ne pouvez pas mettre à jour le nœud de l'appelant. Essayez de changer l'API pour aimer 'n1 = add_first (n1, n2);' (return head) Et l'autre problème est 'sizeof (struct node *)' -> 'sizeof (struct node)' et 'next' n'est pas initialisé. E.g 'n1-> num = 1;' -> 'n1-> num = 1; n1-> suivant = NULL; ' – BLUEPIXY

Répondre

5

La fonction et le programme de test sont incorrects.

Le noeud n1 doit être la tête ne doit-il pas? Cependant, vous affichez la liste passant le nœud n3 au lieu de la tête qui est à la place du nœud n1.

En fait, vous avez construit une liste dont la tête est n3 et n2 et n1 sont ajoutés à la queue de la liste.

Le problème avec la fonction

void add_first(struct node* head, struct node* new_node) { 
    new_node->next = head; 
    head = new_node; 
} 

est que le pointeur vers le noeud head est passé par valeur. Donc, cette déclaration

head = new_node; 

traite une copie de la tête d'origine n1. En fait, la fonction ne change pas n1. Vous devez passer la tête n1 par référence.

Un code correct peut regarder au moins comme

void add_first(struct node **head, struct node *new_node) 
{ 
    new_node->next = *head; 
    *head = new_node; 
} 

Prenez en compte que vous devez définir l'élément suivant les données des noeuds ajoutés à NULL.C'est en principal, vous devez écrire pour chaque noeud créé

n1->num = 1; 
n1->next = NULL; 
n2->num = 2; 
n2->next = NULL; 
n3->num = 3; 
n3->next = NULL; 

La fonction elle-même sera appelé comme

add_first(&n1, n2); 

et

add_first(&n1, n3); 

Dans ce cas, l'affichage de la fonction peut être appelée passer correctement à la tête réelle

display(n1); 

prendre en compte que des déclarations comme celle

n1 = (struct node*)malloc(sizeof(struct node*)); 
             ^^^^^ 

ne sont pas valides. Au lieu de pointeurs, vous devez allouer les nœuds eux-mêmes

n1 = (struct node*)malloc(sizeof(struct node)); 
             ^^^^ 
+0

Merci beaucoup! Il me manquait le fait que la fonction traitait une copie au lieu de la valeur d'origine. Votre explication est extrêmement utile. – Kendra

+0

@Kendra Pas du tout. Je vous en prie.:) –

0

add_first(node,NULL) va effacer les données du pointeur de tête et vous donner une erreur.

et le second cas, si la tête est NULL add_first(NULL,node);