链表头不能跨越函数调用进行更新 [英] Linked List head not being updated across function calls

查看:177
本文介绍了链表头不能跨越函数调用进行更新的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想实现我自己的链接列表,并已与code学习有关动态内存分配和指针和这样瞎搞。当我尝试的东西添加到我的链表,我收到了段错误,并且在使用我意识到调试器,这是因为最初我链表的头指针并没有指向空,然后我的附加功能是不承认的头部是空的。但我有一个设置链表的头指针为NULL的初始化函数,但由于某种原因,我一旦退出初始化函数的出来,到add函数,头不再指向NULL。

I trying to implement my own linked list and have been messing around with the code learning about dynamic memory allocation and pointers and such. When I try to add something to my linked list I get a segfault, and upon using the debugger I realized that it was because initially my linked list's head pointer was not pointing to null and then my add function was not recognizing the head as being empty. But I have an initialize function that is setting the linked list's head pointer to NULL but for some reason once I exit out of the initialize function and into the add function, the head is no longer pointing to NULL.

下面是我的code:

list.h

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

typedef struct list{
    Node *head;
} List;

list.c

list.c

void initialize(List *l){
    if(l != NULL){
        l = malloc(sizeof(List));
        l->head = NULL;
    }
}

void add(List *l, int a){
    //Code
}

int main(){
    List l;
    initialize(&l)
    add(&l, 2);
}

当我踏进add函数,并打印出* L,我看到头不指向为0x0。我一直在抓我的头,为什么它不是。我认为这是一件由价值做通,但我不认为它是。我在做什么错在这里?

As soon as I step into the add function and print out *l, I see that the head is not pointing to 0x0. And I've been scratching my head as to why it's not. I thought it was something to do with pass by value but I don't think it is. What am I doing wrong here?

推荐答案

是的,通过按值就是你的罪魁祸首。你是按值传递的指针。

Yes, pass-by-value is your culprit. You are passing a pointer by value.

假设的main()在地址 0xABCD 。那么你的的main()被编译到

Suppose l in your main() is at address 0xABCD. Then your main() gets compiled to

int main(void) {
    List l;
    initialize(0xABCD);
    add(0xABCD, 2);
}

和您的初始化()调用看起来像这样(假设的malloc()成功,并在地址分配内存 0xCDEF

and your initialize() call looks like this (suppose malloc() succeeds and allocates memory at address 0xCDEF:

void initialize(List *l) {
    if(l != 0x0) {
        l = 0xCDEF;    // malloc()
        l->head = 0x0;
    }
}

这是 L = 0xCDEF 不传播到的main(),因为是按值传递。

That l = 0xCDEF does not propagate to main(), because l was passed by value.

您想要做的是什么

void initialize(List **l) {
    if(l != NULL) {
        *l = malloc(sizeof(List)); // note dereferencing the passed-by-value pointer
        (*l)->head = NULL;
    }
}

int main(void) {
    List * l;
    initialize(&l);
    add(l, 2);
}

这将传递指针的指针的列表(在的main(),它允许在code 初始化()更改变量的main()

which will pass pointer to pointer to list (actually the address of the pointer in your main(). It allows the code in initialize() to change the l variable in main().

另外,你可以使用

List * list_init() {
    List * retval = malloc(sizeof(List));
    if(retval == NULL) { // you should check malloc return value
        // abort(), print warning or just
        return NULL;
    }
    retval->head = NULL;
    return retval;
}

int main(void) {
    List * l = list_init();
    if(l == NULL) {
        // handle the error
    }
    add(l, 2);
}

这篇关于链表头不能跨越函数调用进行更新的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆