2010-08-27 98 views
14

是否有之间的差异:该运营商的其他版本哪个操作员删除?

operator delete(some_pointer); 

delete some_pointer; 

,如果是有什么不同,和其中一个应该使用一个,在哪里? 谢谢。

+0

可能的重复[delete vs delete \ [\]在C++中的运算符](http://stackoverflow.com/questions/2425728/delete-vs-delete-operators-in-c) – 2010-08-27 19:07:40

+0

相关http:// stackoverflow .com/questions/1913343/how-could-pairing-new-with-delete-possible-lead-to-memory-leak-only – 2010-08-27 19:08:08

+2

@ 0A0D:这个问题与数组删除无关。 – UncleBens 2010-08-27 19:14:32

回答

22

具有讽刺意味的是,delete运营商和operator delete()不是一回事。

delete some_pointer;调用some_pointer指向的对象的析构函数,然后调用operator delete()释放内存。

您通常不会直接调用operator delete(),因为如果这样做,对象的析构函数将不会被调用,并且您可能最终会发生内存泄漏。

你唯一需要关心的是operator delete()是当你想通过覆盖operator new()operator delete()做你自己的内存管理。

要知道,你应该知道deletedelete []是两个不同的东西。

+2

这正是我正在寻找的。谢谢。 – 2010-08-27 19:20:37

2

delete some_pointer;是“正确的”使用。

operator delete(some_Pointer);主要存在于定义您自己的删除操作符的语法工件中。也就是说,因为你定义了一个加号运算符为;

myclass::operator+(myclass b) {....} 

你真的可以这样写:

myclass c = a.operator+(b); 

但从来没有人做到这一点。他们使用:

myclass c = a + b; 

同样,你可以写operator delete(some_Pointer);,但从来没有人做过。

+2

他们实际上不是一回事...... – Dima 2010-08-27 19:10:09

+0

@Dima:我在答案的哪一点我说他们是同一个东西?我刚刚说过使用“删除some_Pointer”,你可以,但没有人会使用另一种形式。 – 2010-08-27 19:19:59

+3

你的答案似乎还不清楚...... – 2010-08-27 19:25:40

6

operator delete()只是释放内存。 delete some_pointer调用some_pointer的析构函数,然后调用operator delete()

2

至少在我的经验,这是更常见的实施operator newoperator delete比实际使用(即调用)他们,至少直接。

通常,您间接使用operator newoperator delete - 您会编写new expression,如A *a = new A;。为了实现这一点,编译器生成调用operator new分配原始内存的代码,然后调用一个A::A到原始内存转换为A对象,就像如果你写:

void *temp = operator new(sizeof A); // allocate raw memory with operator new 
A *a = new(temp) A;     // convert raw memory to object with placement new 

当你完成与对象一起使用delete A;。要实现的是,编译器调用该对象的析构函数,然后释放内存,大致是你会做:

a->~A(); 
operator delete(a); 

也有operator [] newoperator [] delete,当/如果你分配/删除其使用数组 - 但在普通版本和阵列版本之间不一定有任何真正的区别 - 它们都只是分配一定数量的原始内存(尽管您可能会猜测数组版本将分配相对较大的内存量,并在此基础上进行一些优化)。

在任何情况下,如果您想优化为特定类的对象分配内存的方式,请将其重载。有许多现有的实现可以放入并使用,特别是在您希望分配大量小对象的情况下,因此您需要最大限度地减少与每个分配相关的开销(例如,Loki的小块HeapLayers分配器)。

一个有趣的小花絮:operator newoperator [] newoperator delete和运营商[]在其声明/定义删除are always静态class members, even if you don't explicitly include static`。

全球有四种版本(::operator new,::operator [] new,::operator delete::operator [] delete)。这些标志着“内部”C++内存管理与外部世界之间的“边界”。通常他们会从操作系统中分配相对较大的内存块,然后根据请求将较小的内存块返回到程序的其余部分。如果你想(尝试)优化你的整个程序的内存管理,你通常会通过重载(或者真的取代)来完成它们。再次,典型的原因是如果你期望分配很多小对象(但不是在几个类中)。其中一个例子是Boost Pool库。

的上述任何直接使用通常只限于在您需要的原料内存块的情况下,对象。一个例子就是实现你自己的容器类。例如,std::vector通常使用::operator new(通过分配器对象)分配存储对象的内存。由于它需要能够分配存储空间,但是只有在以后(或者从不)在该存储中创建对象时,它不能仅仅使用像data = new T[size];这样的东西 - 它必须分配原始内存,然后使用放置new来创建对象将内存添加到集合中时(例如,当您的对象为push_back时)。 std::deque也是如此。如果你想(例如)从头开始实现自己的循环缓冲区,直接处理所有的内存管理,而不是使用类似vector的东西来存储,你可能需要/想要做同样的事情。

+0

谢谢伟大的答案 – 2010-08-28 17:55:08