VC中的delete和delete[]

 VC中的delete和delete[]

很多人在考虑delete和delete[]总是区分基本数据类型和用户自定义类型

 

但是我发现并非如此

int * p = new int[100];
我们调用delete p和delete[] p并没有任何问题,也检查不出内存泄漏

class A
{
public:
    int a;
    A( ) { }
};

A * p = new A[100];
我们调用delete p和delete[] p同样也没有任何问题,也检查不出内存泄漏

class A
{
public:
    int a;
    A( ) { }
    ~A( ) { }
};
A * p1 = new A[100];
A * p2 = new A;
我们调用delete p2和delete[] p1也没有任何问题,没有内存泄漏

但是我们调用delete p1和delete[] p2就立即出错

跟踪发现
void* __cdecl operator new[](size_t nSize, int nType, LPCSTR lpszFileName, int nLine)
{
return ::operator new(nSize, nType, lpszFileName, nLine);
}
void __cdecl operator delete[](void* p)
{
::operator delete(p);
}
从上面的代码来看,new[]就是调用了new,delete[]也同样就是调用delete,为什么会出错呢,检查发现Debug下VC做了一些CRT断言,问题就出在_CrtIsValidHeapPointer这个函数上,这个函数是有源代码的,但不能跟踪无法发现错误,只能看到该函数返回出栈时出错。

那原因究竟在哪?

大家可以看到问题就在那个定义了的析购函数上。

还是继续跟踪有析购函数和无析购函数的情况
class A // 有析购函数
{
public:
    int a;
    A( ) { }
    ~A( ) { }
};
class B // 无析购函数
{
public:
    int b;
    B( ) { }
};

A * p1 = new A[1];
A * p2 = new A;

B * p3 = new B[1];
B * p4 = new B;

跟踪进去,你会发现
p1申请了8个字节
p2申请了4个字节
p3申请了4个字节
p4申请了4个字节

而p1使用delete直接删除就会出错,原因是内存长度不一致,那么多出来的这4个字节做什么用呢,我并没有继续跟下去,我想我差不多能猜出来了,这多出来的指针 。。。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值