簡體   English   中英

全局指針(鏈表頭)未正確更新

[英]Global pointer (head of linked list) not updated properly

在我問這個之前,我已經搜索了很多,但我無法讓這小段代碼工作。
我知道使用global pointer (或變量)被認為是一種不好的做法(而不是通過引用傳遞),但我不得不遺憾地使用這種做法。

我想要做的是制作一個由節點(帶有一些信息的struct )組成的linked list ,並且在每次insert()該列表由一個node動態擴展(除非相關元素已經存在,在這種情況下成員name被覆蓋)。
next指針指向list的下一個元素(這是我從malloc()分配新節點的地方。

程序正確編譯並執行,輸出如下:
在每個printf()調用中retrieve returned: (NULL)
這就是為什么我認為全局指針(列表的頭部)沒有正確更新

我很抱歉這個幼稚的問題,但我似乎無法找到分配/分配出錯的地方,
無論如何,提前感謝您的幫助。

#include <stdio.h>
#include <string.h>
#include <stdlib.h>

struct node{
    char *id;
    char *name;
    struct node *next;
};
struct node* list; //list head
struct node* p; //pointer to list head

char *retrieve(char *id){
    if(list == NULL)
        return NULL; //list is empty, no element to return.
    for(p = list; p != NULL; p = p->next)
        if(strcmp(id, p->id) == 0)
            return p->name;
     return NULL;  
}

void insert(char *id, char *name){
    int exists = 0;
    struct node* temp = NULL;
    for(p = list; p != NULL; p = p->next){
        if(strcmp(id, p->id) == 0){ //id already exists, overwrite with the new name.
            free(p->name);
            p->name = strdup(name);
            exists = 1;
            break;
        }
    }
    if(exists) return; 
    //insert at the end of the list
    temp = malloc(1 * sizeof(struct node));
    if(temp == NULL){
        printf("memory allocation failed\n");
        return;
    }
    temp->id = strdup(id);
    temp->name = strdup(name);
    temp->next = NULL;
    p = temp;
    return;
}

int main(){
    struct node* temp = NULL;
    p = NULL;
    list = NULL;
    insert("145a","Jim");
    insert("246b","Alice");
    insert("322c","Mike");
    printf("retrieve returned: %s\n\n", retrieve("145a"));
    printf("retrieve returned: %s\n\n", retrieve("246b"));
    printf("retrieve returned: %s\n\n", retrieve("322c"));
    p = list;
    while(p != NULL){ // node deletion starting from first to last element.
        free(p->id);
        free(p->name);
        temp = p; 
        p = p->next;
        free(temp);
    }
    return 0;
}

除了使用NULL之外,您永遠不會初始化list 結果,

char *retrieve(char *id){
    if(list == NULL)
        return NULL;

總是返回NULL

void insert(char *id, char *name)
{
    struct node *temp = NULL, **pp;
      /* Pointer to pointer points to the global */    
    for(pp = &list; *pp ; pp = &(*pp)->next){
        if(strcmp(id, (*pp)->id) ) continue;

        free((*pp)->name);
        (*pp)->name = strdup(name);
        return;
        }

    //insert at the end of the list
    temp = malloc(sizeof *temp);
    if(!temp ){
        printf("memory allocation failed\n");
        return;
    }
    temp->id = strdup(id);
    temp->name = strdup(name);
    temp->next = NULL;
    *pp = temp;
    return;
}

你甚至可以不用 *temp 指針:

void insert(char *id, char *name)
{
    struct node **pp;

    for(pp = &list; *pp ; pp = &(*pp)->next){
        if(strcmp(id, (*pp)->id) ) continue;
            free(p->name);
            p->name = strdup(name);
            return;
        }
    // pp now points to the terminal NULL pointer
    *pp = malloc(sizeof **pp);
    if(!*pp ){
        printf("memory allocation failed\n");
        return;
    }
    (*pp)->id = strdup(id);
    (*pp)->name = strdup(name);
    (*pp)->next = NULL;
    return;
}   

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM