有如下代码:
class CTest
{
public:
CTest()
{
m_uiNum = 0;
} ~CTest()
{
}private:
unsigned int m_uiNum;
};int main()
{
std::vector<CTest *> vecter;
unsigned int num = 5;
CTest *pCTest = new CTest[num];
for (unsigned int i=0; i<num; i++)
{
vecter.push_back(pCTest + i);
} std::vector<CTest *>::iterator iter = vecter.begin();
for (; iter!=vecter.end(); iter++)
{
CTest *pTemp = *iter;
if (pTemp != NULL)
{
delete pTemp; //----------语句(1)
}
}
vecter.clear();
}首先new了5个CTest对象,然后放到容器vecter中
最后从vecter中分别取出5个对象进行释放,但是在第一次循环时就抛出异常了如果把5个对象分5次new出来,或者直接 delete [] (*(vecter.begin());就没有问题
难道就是因为这5个对象是一次性分配出来的一块连续内存导致释放单个对象抛出异常了?但是在林锐的《高质量C++编程指南》小册子上有这么一句话://如果用new 创建对象数组,那么只能使用对象的无参数构造函数。例如
Obj *objects = new Obj[100]; // 创建100 个动态对象
//不能写成
Obj *objects = new Obj[100](1);// 创建100 个动态对象的同时赋初值1
在用delete 释放对象数组时,留意不要丢了符号‘[]’。例如
delete []objects; // 正确的用法
delete objects; // 错误的用法
//后者(delete objects)相当于delete objects[0],漏掉了另外99 个对象
问题:
从语句“后者(delete objects)相当于delete objects[0],漏掉了另外99 个对象”,看出在不考虑内存泄露的情况下,至少不会抛出异常
到底是我用错了?还是书上错了,根本就不可以只释放一次性分配的多个对象中的某个对象指针?
请各位大侠解惑,感激不尽!!!

解决方案 »

  1.   

    一次申请一次释放,一次申请了5个想一个个单独释放貌似不可以。
    如果delete时不小心忘了[],并不能说明你还可以再把其它对象一个个地依次释放,要出错的。
    没觉得书上说的有矛盾。
      

  2.   


    但是我在第一次循环中,释放的是分配的内存的首地址:即delete  (*(vecter.begin());,这样也抛出异常了,我这样就相当于delete objects; // 错误的用法
      

  3.   

    程序中开辟的内存在计算机中会有类似于链表的存在
    不可能从中间可以释放,如果一段1000个字节的内存,你不可能从中间释放掉100个字节,上下两部分怎么结合??
    还有对vector 迭代是最好不要释放数据
      

  4.   


    即使我delete分配得到内存的首地址,都报错了,
    如CTest *pCTest = new CTest[5];delete pCTest报错,抛出异常
      

  5.   


    即使我delete分配得到内存的首地址,都报错了,
    如下
    CTest *pCTest = new CTest[5];
    delete pCTest报错,抛出异常但
    CTest *pCTest = new CTest[5];
    delete [] pCTest就没有异常抛出
      

  6.   


    即使我delete分配得到内存的首地址,都报错了,
    如下
    CTest *pCTest = new CTest[5];
    delete pCTest报错,抛出异常但
    CTest *pCTest = new CTest[5];
    delete [] pCTest就没有异常抛出
      

  7.   

    你调式进delete 就应该清楚了
      

  8.   


    1、进到::delete里边到/* verify block type */
                _ASSERTE(_BLOCK_TYPE_IS_VALID(pHead->nBlockUse));这里就出错了难道是检查到释放内存大小与系统记录的所分配的内存大小不一
    致引起的(分配时,分配了 5 * sizeof(CTets),但delete时,由于是(CTest *)类型,所以计算出大小只有sizeof(CTest))?请问是这样的吗?
    2、这个好象是个断言,按理说release版本就没问题了,怎么还是delete还是抱错
    在_CRTIMP PFLS_GETVALUE_FUNCTION __cdecl __set_flsgetvalue()
    {
    #ifdef _M_IX86
        PFLS_GETVALUE_FUNCTION flsGetValue = FLS_GETVALUE;
        if (!flsGetValue)
        {
            flsGetValue = _decode_pointer(gpFlsGetValue);
            TlsSetValue(__getvalueindex, flsGetValue);
        }
        return flsGetValue;
    #else  /* _M_IX86 */
        return NULL;
    #endif  /* _M_IX86 */
    }里边的PFLS_GETVALUE_FUNCTION flsGetValue = FLS_GETVALUE;位置
      

  9.   


    不会啊,没有抛出异常,我以为简单对象和类对象的差异,结果都没有异常。
    int* ppp = new int[1000];
    delete ppp; CRect* pRect = new CRect[1000];
    delete pRect;
    只有内存泄露,没有抛出异常。
      

  10.   


    我的代码如下:class Test
    {
    public:
    Test()
    {
    m_Num = 0;
    } ~Test()
    {
    }private:
    unsigned int m_Num;
    };int _tmain(int argc, _TCHAR* argv[])
    {
    Test *pTest = new Test[1000];
    delete pTest; return 0;
    }运行到delete pTest;
    就抛出异常_BLOCK_TYPE_IS_VALID(pHead->nBlockUse),
    不知道是怎么回事,是否跟工程的配置有关系?
      

  11.   

    去掉析构函数,应该就不会出错了,我做了如下的测试.断点定位到
    _ASSERTE(_BLOCK_TYPE_IS_VALID(pHead->nBlockUse));
    CTest *pT=new CTest[8];
    delete pT;无析构时 pT值是 0x003934dc,_ASSERTE(_BLOCK_TYPE_IS_VALID(pHead->nBlockUse));
    处参数 pUserData也是 0x003934dc 值是一样,pHead->nBlockUse=1,没出错
    有析构时 pT值  0x003934d8, pUserData值一样,但 pHead->nBlockUse=94 出错了换成正确的 delete[] pT形式
    pT值是 0x003934dc,_ASSERTE(_BLOCK_TYPE_IS_VALID(pHead->nBlockUse));
    处参数 pUserData也是 0x003934dc 值是一样,pHead->nBlockUse=1,没出错有析构时 pT值  0x003934dc, pUserData值0x003934d8 值不同,pHead->nBlockUse=1没错
    delete[]形势下,有析构时 pUserData地址小了4,我觉得是编译器加上的...
    所以还是用规范的 delete[]吧
      

  12.   

    我觉得是内存泄露问题![cod
      

  13.   

    程序中开辟的内存在计算机中会有类似于链表的存在
    不可能从中间可以释放,如果一段1000个字节的内存,你不可能从中间释放掉100个字节,上下两部分怎么结合??
    还有对vector 迭代是最好不要释放数据
      

  14.   

    CTest *pCTest = new CTest[2];CTest test1;
    CTest test2;pCTest[0] = test1;
    pCTest[1] = test2;push(&pCTest[0]);
    push(&pCTest[1]);delete (&pCTest[0]); // crash here
    delete (&test1); // crash heredelete[] pCTest;