在 C 中使用 free()

Working of free() in C

我不太理解 C 中的 free() 函数是如何工作的。顾名思义,think free() 所做的就是释放作为参数传递的地址处的内存。然后我尝试了以下代码:

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

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

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

int main()
{
    struct node *first, *second, *temp;
    first = malloc(sizeof(struct node));
    second = malloc(sizeof(struct node));
    temp = first;
    first->data = 1;
    first->next = second;
    second->data = 2;
    second->next = NULL;
    free(first);
    while(temp!=NULL)
    {
        printf("%d\n", temp->data);
        temp = temp->next;
    }
    return 0;
}

以上是一个非常基本的链表实现。我创建了两个节点,即 first 和 second,输入数据并将它们链接在一起。然后我 'freed' 第一个节点,并试图打印链表。 我得到以下输出:

0
2个

所以,这是我的问题,为什么要打印第二个节点?如果第一个节点被释放,那么所有数据和下一个指针都应该被删除。就算我做了

temp = first;

我刚刚将地址从 first 复制到 temp。当我首先释放时,存储在那里的任何东西都应该被销毁,包括第二个节点的地址。那我怎么还能打印第二个节点呢?

问题在于您的假设:

If the first node was freed, then all the data and the next pointer should have been deleted.

您可以释放第一个节点,该内存将 return 放入堆中。它不会(必然)以任何方式进行修改。在您的示例中,指向第二个节点的指针恰好保持不变,因此您仍然可以迭代到它。这就是您能够打印列表中第一个和第二个数字的方式。

基本上,free() 所做的就是说 "This process doesn't care about this block of memory any more"。然后操作系统或其他东西可以使用它。下次您使用 malloc() 时,它可能会再次为您提供相同的内存块。

当然,这都是未定义的行为。这意味着它会很高兴 运行,直到它不高兴为止。