在 C++ 中删除 vs NULL vs free

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/2910587/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-28 11:28:07  来源:igfitidea点击:

delete vs NULL vs free in c++

c++c

提问by hero

what is the difference between deleting a pointer, setting it to null, and freeing it.

删除指针、将其设置为 null 和释放它之间有什么区别。

delete ptr;

vs.

对比

ptr=NULL;

vs.

对比

free(ptr);

回答by j_random_hacker

Your question suggests that you come from a language that has garbage collection. C++ does not have garbage collection.

您的问题表明您来自具有垃圾收集功能的语言。 C++ 没有垃圾收集。

If you set a pointer to NULL, this does not cause the memory to return to the pool of available memory. If no other pointers point to this block of memory, you now simply have an "orphaned" block of memory that remains allocated but is now unreachable -- a leak. Leaks only cause a program to crash if they build up to a point where no memory is left to allocate.

如果将指针设置为 NULL,这不会导致内存返回到可用内存池。如果没有其他指针指向这个内存块,那么您现在只有一个“孤立的”内存块,它仍然分配但现在无法访问——泄漏。泄漏只会导致程序崩溃,如果它们累积到没有内存可分配的程度。

There's also the converse situation, where you deletea block of memory using a pointer, and later try to access that memory as though it was still allocated. This is possible because calling deleteon a pointer does not set the pointer to NULL -- it still points to the address of memory that previously was allocated. A pointer to memory that is no longer allocated is called a dangling pointerand accessing it will usually cause strange program behaviour and crashes, since its contents are probably not what you expect -- that piece of memory may have since been reallocated for some other purpose.

还有一种相反的情况,您delete使用指针的内存块,然后尝试访问该内存,就好像它仍然被分配一样。这是可能的,因为调用delete指针不会将指针设置为 NULL —— 它仍然指向先前分配的内存地址。不再分配的内存指针称为悬空指针,访问它通常会导致奇怪的程序行为和崩溃,因为它的内容可能不是你所期望的——那块内存可能已经被重新分配用于其他目的.

[EDIT]As stinky472 mentions, another difference between deleteand free()is that only the former calls the object's destructor. (Remember that you must call deleteon an object allocated with new, and free()for memory allocated with malloc()-- they can't be mixed.) In C++, it's always best to use static allocation if possible, but if not, then prefer newto malloc().

[编辑]正如 stinky472 所提到的,delete和之间的另一个区别free()是只有前者调用对象的析构函数。(请记住,您必须调用delete使用 分配的对象new,而free()对于分配的内存,malloc()它们不能混合使用。)在 C++ 中,如果可能,最好始终使用静态分配,但如果不是,则更喜欢new使用malloc()

回答by Lucas

deletewill give allocated memory back to the C++ runtime library. You always need a matching new, which allocated the memory on the heap before. NULLis something completely different. A "placeholder" to signify that it points to no address. In C++, NULLis a MACRO defined as 0. So if don't like MACROS, using 0directly is also possible. In C++0x nullptris introduced and preferable.

delete将分配的内存返回给 C++ 运行时库。您总是需要一个匹配的new,它之前在堆上分配了内存。NULL是完全不同的东西。一个“占位符”,表示它没有指向地址。在 C++ 中,NULL是一个宏定义为0. 所以如果不喜欢宏,0直接使用也是可以的。在 C++0x 中nullptr被引入并且是优选的。

Example:

例子:

int* a;        //declare pointer
a = NULL;      //point 'a' to NULL to show that pointer is not yet initialized 
a = new int;   //reserve memory on the heap for int

//... do more stuff with 'a' and the memory it points to

delete a;      //release memory
a = NULL;      //(depending on your program), you now want to set the pointer back to
               // 'NULL' to show, that a is not pointing to anything anymore

回答by foret

well, if you created object dynamically(with 'new'), setting pointer to any value does not delete object from memory - and you get a memory leak.

好吧,如果您动态创建对象(使用“new”),则将指针设置为任何值都不会从内存中删除对象 - 并且您会出现内存泄漏。

回答by sbi

As with any indirection, there are two objectsinvolved when using pointers: the referrer(the pointer, in your example ptr) and the referenced object(what it points to, *ptr). You need to learn to differentiate between them.

与任何间接方式一样,使用指针时涉及两个对象引用者(在您的示例中为指针ptr)和被引用对象(它指向的对象*ptr)。你需要学会区分它们。

When you assign NULLto a pointer, only the pointer is affected, the object it refers to is left alone. If the pointer was the last one pointing to that object, you have lost the last referring pointerpointing to it and thus cannot use it anymore. In C++, however, that does not mean the object will be deleted. C++ does not have a garbage collection. So the object is leaked.

当您分配NULL给一个指针时,只有该指针受到影响,它所引用的对象不会被影响。如果该指针是最后一个指向该对象的指针,则您已经丢失了指向它的最后一个引用指针,因此无法再使用它。然而,在 C++ 中,这并不意味着对象将被删除。C++ 没有垃圾收集。所以对象被泄露了

In order for objects to be deleted, you will have to delete them manuallyby passing their address (stored in a pointer) to the deleteoperator. If you do this, only the object referred towill be affected, the pointer is left alone. It might still point to the address where the object resided in memory, even though that isn't usable anymore. That is called a dangling pointer.

为了删除对象,您必须通过将它们的地址(存储在指针中)传递给操作员来手动删除它们delete。如果你这样做,只有被引用的对象会受到影响,指针不会被影响。它可能仍然指向对象驻留在内存中的地址,即使它不再可用。那就是所谓的悬空指针

回答by jasonline

When you create an object using new, you need to use delete to release its memory back to the system. The memory will then be available for others to reuse.

当您使用 new 创建对象时,您需要使用 delete 将其内存释放回系统。内存将可供其他人重用。


int* a = new int;
delete a;

NULL is just a pre-defined macro that can be assigned a pointer to mean that it does not point to anything.

NULL 只是一个预定义的宏,可以分配一个指针来表示它不指向任何东西。


int* a = new int;
a = NULL;

In the above case, after allocating storage for a, you are assigning NULL to it. However, the memory previously allocated for a was not released and cannot be reused by the system. This is what we call memory leak.

在上述情况下,在为 a 分配存储空间后,您将为其分配 NULL。但是,之前为a分配的内存并没有被释放,系统无法重用。这就是我们所说的内存泄漏。

回答by Vijay Singh

int * ptr = null;

Calling free(ptr)will do nothing. According to standard if given pointer is null then no action happens.

打电话free(ptr)什么都不会。根据标准,如果给定的指针为空,则不会发生任何操作。

Using delete pwill also do nothing. C++ standard says that no action will happen because it points to nothing and no type is available.

使用delete p也无济于事。C++ 标准说不会发生任何动作,因为它指向什么也没有类型可用。