C-不能在链接列表的前面

问题描述

我正在按照here上的教程进行操作,以建立链接列表。我无法使用“将项目添加到列表的开头(推到列表)”部分。

我的代码

node_t* prepend(node_t **head,int val) {
    //create new node pointer
    node_t *new_node = (node_t*) malloc(sizeof(node_t));
    new_node->val = val;
    new_node->next = *head; //set its next to existing head (pointer of pointer)
    //update existing head to point to new node
    *head = new_node;
    return *head;
}

int my_first_ll() {

    //define a local variable called head that will point to the first node
    node_t *head = NULL;
    head = (node_t*) malloc(sizeof(node_t));

    //check for null pointer
    if (head == NULL) {
        return 1;
    }

    //note how because head is a pointer we're using -> rather than dot notation to access attributes
    head->val = 1;
    head->next = (node_t*) malloc(sizeof(node_t));
    head->next->val = 2;
    head->next->next = NULL; //last item should point to a NULL

    head = prepend(head,0);
    print_list(head);
}

它打印:

Currently at node 0

代替

Currently at node 0
Currently at node 1
Currently at node 2

因此,当我插入新的标头时,似乎无法链接到上一个标头-但我不知道如何操作。

解决方法

我找到了一个解决方案:与其像本教程中一样将**head传递给prepend,而是传递*head可以解决问题。最终的代码如下:

node_t* prepend(node_t *head,int val) {
    //create new node pointer
    node_t *new_node = (node_t*) malloc(sizeof(node_t));
    new_node->val = val;
    new_node->next = head; //set its next to existing head (pointer of pointer)
    //update existing head to point to new node
    head = new_node;
    return head;
}

有人可以解释为什么一个有效而另一个无效吗?为什么他们在本教程中使用两颗星?如果两颗星实际上是正确的,那为什么对我来说却失败了?

,

您可以将**head传递给该函数,因此基本上可以将指针传递给指针:

void prepend(node_t **head,int data){
    node_t *new = malloc(sizeof(node_t));
    //set data
    new->data = data;  
    //set the next pointer of new to current head                
    new->next = *head; 
    //now set the newly created node to be the new head                     
    *head = new;                            
}

但是您必须这样调用函数:

int main()
{
    node_t *head = NULL;
    prepend(&head,3);
    prepend(&head,6);
    printlist(head);
    deltelist(&head);
    return 0;
}

并且没有理由在函数中返回*head,因为您基本上更改了在main中创建的头节点。 因此,如果我现在打印列表,它将打印

6
3

使用完列表后,别忘了删除列表。

希望这对您有所帮助:)