繁体   English   中英

释放等于malloc指针的指针

[英]Free a pointer equal to a malloc pointer

我在理解某些free()行为时遇到了麻烦。

int* ptr1 = (int*)malloc(sizeof (int)*10);
int* ptr2 = ptr1;
free(ptr2);

free(ptr2)会根据需要删除我的数组?

如果我该怎么办:

int** ptr1 = (int**)malloc(sizeof (int)*10);
int* ptr2 = (int*)malloc(sizeof (int));
*ptr2 = 10;
ptr1[0] = ptr2;
free(ptr1);

此代码正确吗? free(ptr1)也会删除ptr2的空间吗?

谢谢

是和否。

另请注意, malloc(sizeof(int)*10); 在第二个示例中可以使用,但不一定会为十个指针分配空间。


为了解释在第一个示例中发生的情况,在分配给ptr2之后,您将获得以下内容:

+------+
| ptr1 | ---\
+------+     \      +----------------------------+
              >---> | memory allocated by malloc |
+------+     /      +----------------------------+
| ptr2 | ---/
+------+

这两个变量包含相同的值,即malloc返回的指针,因此您可以使用它们之一来访问分配的内存。

对于第二个问题,您所拥有的是这样的:

+---------+---------+---------+-----+
| ptr1[0] | ptr1[1] | ptr1[2] | ... |
+---------+---------+---------+-----+
  |
  |
  v
+----------------------------+
| memory allocated by malloc |
+----------------------------+
  ^
  |
  |
+------+
| ptr2 |
+------+

当您释放内存指针ptr1 ,只有释放内存,内存指向ptr2仍然存在且可通过ptr2

mallocfree不了解您的数据结构。 他们所知道的只是字节的斑点。

通常,您的mallocfree调用之间应该存在一对一的关系。 (有很多例外,但这是一个很好的一般规则。)

从来没有一次调用free会同时释放两次调用malloc分配的两个单独的块。

因此,正如其他人所说,您的问题的答案是“是”和“否”。

int* ptr1 = (int*)malloc(sizeof(int)*10);
int* ptr2 = ptr1;
free(ptr2);

很好, ptr2包含与ptr1相同的值,因此您传递给malloc()的内存为free() d。

int** ptr1 = (int**)malloc(sizeof(int)*10);
int* ptr2 = (int*)malloc(sizeof(int));
*ptr2=10;
ptr1[0]=ptr2;
free(ptr1);

那不好 您正在将ptr2的值存储在ptr1数组中,但没有释放它。 你要:

int** ptr1 = (int**)malloc(sizeof(int*)*10);
int* ptr2 = (int*)malloc(sizeof(int));
*ptr2=10;
ptr1[0]=ptr2; 
...
free(ptr1[0]);
free(ptr1);

注意,我还更改了malloc()以分配10个指向int指针,而不仅仅是分配10个int (其大小可能不相同)。

最后请注意,您不需要在C中malloc()的返回值 。我没有为您解决此问题,因为它本身不是问题,并且与您的问题无关,但是(可以说)不好样式。

free(ptr2)是否会根据需要删除我的数组?

我认为delete一词在这里不能使用。 GNU手册说:

当不再需要使用malloc获得的块时,请使用free函数使该块可再次分配。

但是free不会将指针自动设置为NULL,因为函数返回类型本身为void 也,

释放一个块会改变该块的内容。 释放数据后,不要期望在该数据块中找到任何数据(例如,指向链中下一个块的指针)。

我并没有引发关于是否应在释放指针后将其设置为NULL的争论。 但是,我很想发布这个崩溃和烧伤的示例:

#include<stdio.h>
#include<stdlib.h>
int main()
{
    int* ptr1 = malloc(sizeof(int)*10);
    int* ptr2 = ptr1;
    free(ptr2);
    if(ptr2!=NULL)
    {
        printf("ptr is %p\n",ptr2); // still printf
        printf("Enter a number for ptr2 :");
        scanf("%d",ptr2);
        printf("Value pointed to by ptr2 : %d\n",*ptr2);
        printf("Value pointed to by ptr1 : %d\n",*ptr1);
    }
    else
        printf("Ptr2 pointed to null");
    printf("Size of ptr1 : %d\n",sizeof(ptr1));

    if(ptr1==NULL)
        printf("ptr1 NULL\n");
    printf("Enter a number for ptr1 :");
    scanf("%d",ptr1);
    printf("Value pointed to by ptr1 : %d\n",*ptr1);
    printf("Value pointed to by ptr2 : %d\n",*ptr2);

    free(ptr1);
    if(ptr1==NULL)
        printf("ptr1 freed\n");

    return 0;
}

产量

ptr is 0x1c92010
Enter a number for ptr2 :4
Value pointed to by ptr2 : 4
Value pointed to by ptr1 : 4
Size of ptr1 : 8
Enter a number for ptr1 :1
Value pointed to by ptr1 : 1
Value pointed to by ptr2 : 1
*** glibc detected *** ./testp: double free or corruption (fasttop): 0x0000000001c92010 ***
Segmentation fault (core dumped)

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM