首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >关于delete、delete[]、操作符delete()等

关于delete、delete[]、操作符delete()等
EN

Stack Overflow用户
提问于 2010-09-02 09:21:47
回答 1查看 841关注 0票数 4

可能重复:

How does delete[] “know” the size of the operand array?

( POD )freeing memory : is delete[] equal to delete ?

据我所知,

代码语言:javascript
复制
class A {};
A* a = new A;
//
delete A;

首先调用operator new() (全局调用,或A提供的专用调用)分配正确的内存量,然后调用A的构造函数,当调用delete时,is将首先调用A的析构函数,然后调用operator delete()来释放“正确的内存量”。

正如我在TC++PL中所读到的,这个“正确的内存量”是这样确定的:

要释放由new、delete和delete[]分配的空间,

必须能够确定所分配对象的大小。这意味着使用new的标准实现分配的对象将比静态对象占用更多的空间。通常,一个单词用于保存对象的大小。

这说得通。但是delete把这个词存储在哪里才能访问呢?就在新指针指向的地址之前?以便delete可以通过访问a-sizeof<void*>获得要删除的大小?

你能澄清这一点吗?

我认为答案可能会帮助我理解delete []是如何工作的。我理解new []将如何工作,delete []将首先为“数组的所有对象”调用析构函数,然后释放所有这些内存.

但是delete []如何知道数组的大小呢?

谢谢你有帮助的答案!

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2010-09-02 09:29:37

这一切都取决于执行情况。

大多数运行时确实会在返回内存((BYTE *)p-sizeof(size_t))之前存储内存大小,但还有其他选择。在我自己的内存管理器(是的,我写了这类东西)中,我有一个更复杂的数据结构(使用指向链接列表、校验和、.)的指针。在返回的记忆之前。实际上,要由内存管理器来决定在哪里存储这些信息。

除了分配内存的大小之外,new[]还将存储实例的数量,以便知道要调用多少析构函数。这通常超出了内存管理器的范围,通常由C++运行时/编译器自己处理。但是,这几个实例存储的位置取决于编译器,尽管实际上我希望它存储在返回内存之前(以及内存管理器存储的任何数据之后)。

编辑:下面的小实用程序显示了分配内存之前的内存布局:

代码语言:javascript
复制
#include <iostream>

typedef unsigned char Byte;

class X
   {
   public:
      X() : m_value(1) {}
      ~X() {m_value = 0;}
   private:
      int m_value;
   };

void print(Byte *p,int offset)
{
printf ("Value at %d: 0x%x (%d)\n", offset, p[offset], p[offset]);
}

void main()
{
X *x = new X[10];

std::cout << "Address of x: " << x << std::endl;
std::cout << "sizeof(X)   : " << sizeof(X) << std::endl;

Byte *p = (Byte *)x;
print(p,-1);
print(p,-2);
print(p,-3);
print(p,-4);
print(p,-5);
print(p,-6);
print(p,-7);
print(p,-8);
print(p,-9);
print(p,-10);

X *y = new X;
std::cout << "Address of y: " << y << std::endl;

p = (Byte *)y;
print(p,-1);
print(p,-2);
print(p,-3);
print(p,-4);
print(p,-5);
print(p,-6);
print(p,-7);
print(p,-8);
print(p,-9);
print(p,-10);
}

运行此操作将提供以下输出(在Visual 2005上):

代码语言:javascript
复制
Address of x: 00481DE4
sizeof(X)   : 4
Value at -1: 0x0 (0)
Value at -2: 0x0 (0)
Value at -3: 0x0 (0)
Value at -4: 0xa (10)
Value at -5: 0xc (12)
Value at -6: 0x0 (0)
Value at -7: 0x2f (47)
Value at -8: 0x8 (8)
Value at -9: 0x2f (47)
Value at -10: 0x98 (152)
Address of y: 00481E70
Value at -1: 0xc (12)
Value at -2: 0x0 (0)
Value at -3: 0x2f (47)
Value at -4: 0x8 (8)
Value at -5: 0x2a (42)
Value at -6: 0x98 (152)
Value at -7: 0xf8 (248)
Value at -8: 0xb0 (176)
Value at -9: 0x0 (0)
Value at -10: 0x48 (72)

您可以清楚地看到,在第一种情况下( new[]'d数组),有4个字节用来表示元素的数量(0,0,0,10,这使值10相加)。

在第二种情况下,省略这些字节,我们看到与第一种情况相同的模式(12,0,47,8)。我不知道Visual到底在哪里存储分配的字节数,但它证明元素的数量确实存储在返回的指针之前(在Visual 2005中)。

票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/3625718

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档