C将节点添加到链表头部

我在c中创建了一个链表结构

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

在列表开头添加节点的方法:

 void addFirst(struct node *list, int value){ struct node *new_node = (struct node*) malloc (sizeof (struct node)); new_node->value = value; new_node->next = list; list = new_node; } 

我创建了一个列表(malloc和所有东西),然后调用这个方法,它在方法中添加新节点但是当我回到我的主要时,我的旧列表保持不变。 使用DDD调试器检查所有内容。 这怎么可能? 我无法更改方法签名,所以必须这样做。

如果你真的需要这样做,你必须重新投射指针。 像这样的东西:

 struct node *my_list = null; addFirst((struct node *)&my_list, 123); void addFirst(struct node *list, int value){ struct node **real_list = (struct node **)list; struct node *new_node = (struct node*) malloc (sizeof (struct node)); new_node->value = value; new_node->next = *real_list; *real_list = new_node; } 

节点指针无法以这种方式更改为函数。 在函数中,您可以更改指针的内容而不是指针的地址。 你必须传递指针struct node **list的指针

在这之后怎么做:

 void addFirst(struct node **list, int value){ struct node *new_node = (struct node*) malloc (sizeof (struct node)); new_node->value = value; new_node->next = *list; *list = new_node; } 

或者你可以这样做

 struct node * addFirst(struct node *list, int value){ struct node *new_node = (struct node*) malloc (sizeof (struct node)); new_node->value = value; new_node->next = list; return new_node; } 

在你的鳕鱼中你可以在调用这个函数后获得头部

 head = addfirst(head,45); 

在C中,如果希望函数能够更改其参数中接收的值,则需要传递该值的地址。 因此,要更改列表指针的值,您需要传递列表指针的地址。 你的addFirst()函数应如下所示:

 void addFirst(struct node **list, int value){ struct node *new_node = (struct node*) malloc (sizeof (struct node)); new_node->value = value; new_node->next = *list; *list = new_node; } 

在调用该函数时,您可以这样调用它:

 addFirst(&list, value); 

现在,如果你想保留函数的签名,可能会改变你考虑头节点的方式。 如果你声明你的头节点只是为了保存指向第一个值的指针,但是它本身不包含一个值,你可以这样做:

 struct node *head; void addFirst(struct node *list, int value){ struct node *new_node = (struct node*) malloc (sizeof (struct node)); new_node->value = value; new_node->next = list->next; list->next = new_node; } addFirst(head, 45); 

现在,您只需更改列表中的所有函数,以便它们工作相同,以便认为“head”仅指向列表的真实第一个节点,但不是列表本身的成员。 出于所有实际目的,“真正的”头部是 – >接下来。

我已经学会了@Vlad Lazarenko的答案,我就这样制作了代码,是不是?

 addFirst((struct node**)head,123); void addFirst(struct node **list,int value) { struct node *new_node=malloc(sizeof(struct node)); new_node->value=value; new_node->next=*list; list=&new_node; } 
 void addFirst(struct node **list, int value){ struct node *new_node = (struct node*) malloc (sizeof (struct node)); new_node->value = value; new_node->next = *list; *list = new_node; } 

这是正确的代码。 问题是你传递的poineter struct node *list不能改变,因为它是一个堆栈变量。 如果将其更改为struct node **list ,则会将指针传递给struct node **list的第一个节点。 现在您可以将其更改为指向列表的新第一个节点。

一切都很好,但在void addFirst(struct node *list, int value)函数中, list按值传递。 这意味着正在复制指针, addFirst函数调用者看addFirst函数内的该指针的新地址。 要解决它,你必须通过指针( struct node ** )传递指针或使其成为返回值并要求调用者将其用作新的“头”。

别忘了; 在结构声明之后。