为什么我的指针在空闲后不为空?

时间:2022-11-03 21:18:01
void getFree(void *ptr)
{
    if(ptr != NULL)
    {
        free(ptr);
        ptr = NULL;
    }
    return;
}
int main()
{
char *a;
a=malloc(10);
getFree(a);
if(a==NULL)
    printf("it is null");
else
    printf("not null");
}

Why is the output of this program not NULL?

为什么这个程序的输出不是NULL?

5 个解决方案

#1


19  

Because the pointer is copied by value to your function. You are assigning NULL to the local copy of the variable (ptr). This does not assign it to the original copy.

因为指针是按值复制到您的函数。您正在为变量的本地副本(ptr)分配NULL。这不会将其分配给原始副本。

The memory will still be freed, so you can no longer safely access it, but your original pointer will not be NULL.

内存仍将被释放,因此您无法再安全地访问它,但您的原始指针不会为NULL。

This the same as if you were passing an int to a function instead. You wouldn't expect the original int to be edited by that function, unless you were passing a pointer to it.

这就像将int传递给函数一样。您不希望该函数编辑原始int,除非您传递指向它的指针。

void setInt(int someValue) {
    someValue = 5;
}

int main() {
    int someOtherValue = 7;
    setInt(someOtherValue);
    printf("%i\n", someOtherValue); // You'd expect this to print 7, not 5...
    return 0;
}

If you want to null the original pointer, you'll have to pass a pointer-to-pointer:

如果要使原始指针为空,则必须传递指向指针的指针:

void getFree(void** ptr) {
    /* Note we are dereferencing the outer pointer,
    so we're directly editing the original pointer */

    if (*ptr != NULL) {
        /* The C standard guarantees that free() safely handles NULL,
           but I'm leaving the NULL check to make the example more clear.
           Remove the "if" check above, in your own code */
        free(*ptr);
        *ptr = NULL;
    }

    return;
}

int main() {
    char *a;
    a = malloc(10);

    getFree(&a); /* Pass a pointer-to-pointer */

    if (a == NULL) {
        printf("it is null");
    } else {
        printf("not null");
    }

    return 0;
}

#2


7  

Because the getFree() function takes a copy of the pointer. ptr and c are both pointers, but they are different variables. It's the same reason why this function will output "6":

因为getFree()函数接受指针的副本。 ptr和c都是指针,但它们是不同的变量。这个函数输出“6”的原因相同:

void Magic(int x)
{
    x = 1;
}

void main()
{
    int a = 6;
    Magic(a);
    printf("%d", a);
}

#3


4  

You are passing pointer a by value, so it is not modified by function. It's only a copy of pointer modified within function, the original variable value is not affected.

您正在按值传递指针,因此不会被函数修改。它只是在函数内修改的指针的副本,原始变量值不受影响。

Update:

If you wanted to make your life easier by replacing freeing + nulling a variable with a single line of code, you need either a macro:

如果您希望通过使用单行代码替换释放+归零变量来简化您的生活,则需要一个宏:

#define MYFREE(x) free(x); x = NULL;

or a function with pointer to pointer argument:

或者指向指针参数的函数:

void myfree(void** pp) { free(*pp); *pp = NULL; }

#4


3  

Pointers are stored as integers somewhere in memory.

指针在内存中的某处存储为整数。

When you do a = malloc(10);, a has some value, say 0x1.

当你执行a = malloc(10);时,a有一些值,比如说0x1。

When you call getFree(a);, the function copies a into void *ptr.

当你调用getFree(a);时,该函数将a复制到void * ptr中。

Now a=0x1 and ptr=0x1.

现在a = 0x1,ptr = 0x1。

When you do ptr=NULL, only ptr is changed to NULL, but a is still 0x1..

当你执行ptr = NULL时,只有ptr被更改为NULL,但是仍然是0x1 ..

#5


1  

You are passing the pointer By value.. (By default C passes the argument by value) which means you are updating the copy only ..not the real location..for that you might need to use pointer to pointer in C

你正在传递指针By值..(默认情况下C通过值传递参数)这意味着你只更新副本..不是真正的位置..因为你可能需要在C中使用指针指针

void getFree(void **ptr)
{

    if(*ptr != NULL)
    {
        free(*ptr);
        *ptr = NULL;
    }

    return;
}

#1


19  

Because the pointer is copied by value to your function. You are assigning NULL to the local copy of the variable (ptr). This does not assign it to the original copy.

因为指针是按值复制到您的函数。您正在为变量的本地副本(ptr)分配NULL。这不会将其分配给原始副本。

The memory will still be freed, so you can no longer safely access it, but your original pointer will not be NULL.

内存仍将被释放,因此您无法再安全地访问它,但您的原始指针不会为NULL。

This the same as if you were passing an int to a function instead. You wouldn't expect the original int to be edited by that function, unless you were passing a pointer to it.

这就像将int传递给函数一样。您不希望该函数编辑原始int,除非您传递指向它的指针。

void setInt(int someValue) {
    someValue = 5;
}

int main() {
    int someOtherValue = 7;
    setInt(someOtherValue);
    printf("%i\n", someOtherValue); // You'd expect this to print 7, not 5...
    return 0;
}

If you want to null the original pointer, you'll have to pass a pointer-to-pointer:

如果要使原始指针为空,则必须传递指向指针的指针:

void getFree(void** ptr) {
    /* Note we are dereferencing the outer pointer,
    so we're directly editing the original pointer */

    if (*ptr != NULL) {
        /* The C standard guarantees that free() safely handles NULL,
           but I'm leaving the NULL check to make the example more clear.
           Remove the "if" check above, in your own code */
        free(*ptr);
        *ptr = NULL;
    }

    return;
}

int main() {
    char *a;
    a = malloc(10);

    getFree(&a); /* Pass a pointer-to-pointer */

    if (a == NULL) {
        printf("it is null");
    } else {
        printf("not null");
    }

    return 0;
}

#2


7  

Because the getFree() function takes a copy of the pointer. ptr and c are both pointers, but they are different variables. It's the same reason why this function will output "6":

因为getFree()函数接受指针的副本。 ptr和c都是指针,但它们是不同的变量。这个函数输出“6”的原因相同:

void Magic(int x)
{
    x = 1;
}

void main()
{
    int a = 6;
    Magic(a);
    printf("%d", a);
}

#3


4  

You are passing pointer a by value, so it is not modified by function. It's only a copy of pointer modified within function, the original variable value is not affected.

您正在按值传递指针,因此不会被函数修改。它只是在函数内修改的指针的副本,原始变量值不受影响。

Update:

If you wanted to make your life easier by replacing freeing + nulling a variable with a single line of code, you need either a macro:

如果您希望通过使用单行代码替换释放+归零变量来简化您的生活,则需要一个宏:

#define MYFREE(x) free(x); x = NULL;

or a function with pointer to pointer argument:

或者指向指针参数的函数:

void myfree(void** pp) { free(*pp); *pp = NULL; }

#4


3  

Pointers are stored as integers somewhere in memory.

指针在内存中的某处存储为整数。

When you do a = malloc(10);, a has some value, say 0x1.

当你执行a = malloc(10);时,a有一些值,比如说0x1。

When you call getFree(a);, the function copies a into void *ptr.

当你调用getFree(a);时,该函数将a复制到void * ptr中。

Now a=0x1 and ptr=0x1.

现在a = 0x1,ptr = 0x1。

When you do ptr=NULL, only ptr is changed to NULL, but a is still 0x1..

当你执行ptr = NULL时,只有ptr被更改为NULL,但是仍然是0x1 ..

#5


1  

You are passing the pointer By value.. (By default C passes the argument by value) which means you are updating the copy only ..not the real location..for that you might need to use pointer to pointer in C

你正在传递指针By值..(默认情况下C通过值传递参数)这意味着你只更新副本..不是真正的位置..因为你可能需要在C中使用指针指针

void getFree(void **ptr)
{

    if(*ptr != NULL)
    {
        free(*ptr);
        *ptr = NULL;
    }

    return;
}