C 为什么在复制链接列表时会指定此指针?

C 为什么在复制链接列表时会指定此指针?,c,memory-management,linked-list,C,Memory Management,Linked List,在此代码中: Node *CopyList(Node **head) { Node *current = *head; Node *NewNode = NULL; Node *tail = NULL; while (current != NULL ) { if (NewNode == NULL) { NewNode = malloc(sizeof(Node)); NewNode->data =

在此代码中:

Node *CopyList(Node **head) {
    Node *current = *head;
    Node *NewNode = NULL;
    Node *tail = NULL;

    while (current != NULL ) {
        if (NewNode == NULL) {
            NewNode = malloc(sizeof(Node));
            NewNode->data = current->data;
            NewNode->next = NULL; // routine
            tail = NewNode;
        } else {
            tail->next = malloc(sizeof(Node)); // here 
            tail = tail->next;
            tail->data = current->data;
            tail->next = NULL;
        }
        current = current->next;
    }
    return(NewNode);
}
为什么我们要将
tail->next
分配给
malloc()
调用的结果?显然,如果我们不这样做,就会出现分段错误


为什么我们不直接分配
tail
而不是
tail->next
?接下来我应该在哪些情况下这样分配?

这只是为了方便起见,避免使用额外的变量:

Node* temp = malloc(sizeof(Node)); // here 
temp->data = current->data ;
temp->next = NULL ;

tail->next = temp ;
tail = tail->next;
为什么我们不直接分配tail,而是tail->next


Tail已经分配,它作为上一个节点,所以我们可以将它链接到下一个节点。我们分配一个新节点,并使用tail->next=该节点将tail链接到该节点。

这里NewNode表示新的链表头。因此,在while循环中,它第一次被分配,这样下次就不会被更改了。对于您的问题,使用“tail->next”而不是“tail”,因为第一次执行“NewNode==NULL”然后执行“tail=NewNode”意味着tail具有新节点地址。所以下一步,您需要将下一个块复制到“tail->next”中,因为tail已经有了“NewNode”。

这段代码似乎是合理的。在第一次迭代中,它分配新列表的头部(
NewNode
),在随后的每次迭代中,它扩展新列表的尾部。你认为这有什么问题?不应该因为
tail
而出现segfault,因为它在使用时不会为NULL。这里唯一的错误是没有检查
malloc
的返回值是否为NULL。我不认为这是错误的,只是我没有理解它。很抱歉,我仍然没有理解它,你说我需要将下一个块复制到“tail->next”是什么意思?请你解释得更详细一点好吗?如果“tail=NewNode”意味着NewNode被分配到tail,则使用in first。现在在else部分中,您应该将下一个块复制到tail,这意味着您需要将新块分配到“tail->next”,因为tail已经有了新节点。一旦您尝试通过获取具有2个以上节点的链表进行干运行。那你就很容易得到它