Справочник функций

Ваш аккаунт

Войти через: 
Забыли пароль?
Регистрация
Информацию о новых материалах можно получать и без регистрации:

Почтовая рассылка

Подписчиков: -1
Последний выпуск: 19.06.2015

Не могу понять ошибку

16K
30 марта 2006 года
KAPJICOH
4 / / 30.03.2006
Вот код двух методов класса:
Код:
bool CMap::CreateMesh(STRING mClass)
{
    CHARMESHDEF mesh;
    for(unsigned short i=0;i<pDefine->GetCharMeshDefAr()->GetSize();i++)
    {
        if(strcmp(pDefine->GetCharMeshDefAr()->GetAt(i+1).name.GetString(),mClass.GetString())==0)
        {
            mesh = pDefine->GetCharMeshDefAr()->GetAt(i+1);
            break;
        }
        if(i==pDefine->GetCharMeshDefAr()->GetSize()-1)
        {
            AfxMessageBox("Cannot find class!",MB_OK,NULL);
            return false;
        }
    }

    CMesh newMesh;
    if(newMesh.LoadMesh(mesh.modelPath))
        Add(newMesh);
    else
        return false;

      return true;
}

void CMap::Add(CMesh value)
{
    if(meshNum==0)
    {
        meshNum++;
        mapMesh = new CMesh[meshNum];
        mapMesh[0] = value;
        return;
    }

    CMesh* temp;
   
    temp = new CMesh[meshNum];
    for(unsigned int i=0;i<meshNum;i++)
        temp = mapMesh;
    delete [] mapMesh;
    mapMesh = new CMesh[meshNum+1];
    for(i=0;i<meshNum;i++)
        mapMesh = temp;
    mapMesh[meshNum] = value;
    meshNum++;
    delete [] temp;
}

При возвращении из функции Add класс newMesh теряет всю информацию(в debuge пишет <bad ptr>), затем вызывается деструктор класса newMesh и выводится сообщение об ошибке. Подскажите почему после вызова Add newMesh теряет информацию? Заранее спасиба.
324
30 марта 2006 года
AndreySar
532 / / 01.08.2004
Цитата:
Originally posted by KAPJICOH
Вот код двух методов класса:
...
При возвращении из функции Add класс newMesh теряет всю информацию(в debuge пишет <bad ptr>), затем вызывается деструктор класса newMesh и выводится сообщение об ошибке. Подскажите почему после вызова Add newMesh теряет информацию? Заранее спасиба.

534
30 марта 2006 года
HarryAxe
448 / / 19.01.2006
Цитата:
Originally posted by KAPJICOH
Вот код двух методов класса:
Код:
void CMap::Add(CMesh value)
{
    temp = new CMesh[meshNum];
    for(unsigned int i=0;i<meshNum;i++)
        temp = mapMesh;
    delete [] mapMesh;
    mapMesh = new CMesh[meshNum+1];
    for(i=0;i<meshNum;i++)
        mapMesh = temp;
    mapMesh[meshNum] = value;
    meshNum++;
    delete [] temp;
}

Подскажите почему после вызова Add newMesh теряет информацию? Заранее спасиба.


Во первых, там, где члены массива добавляются/удаляются динамически, лучше было бы использовать не массивы, а связанные списки или вектора из stl, тогда всё будет работать гораздо быстрее. Во-вторых, я полагаю, параметр value в Add() лучше будет передавать по ссылке: Add(CMesh & value), а ещё лучше Add(const CMesh & value), если ты не планируешь изменять параметр, тогда тебе проще было бы найти свою ошибку. А связана она у тебя с удалением массива и отсутствием конструктора копий. Компилятор выполняет строчку temp = mapMesh путём простого копирования всех переменных класса CMesh, то есть те самые переменные, которые содержатся в public/private/protected секциях. Но вот ту память, которую выделяет уже сам экземпляр класса в процессе своей работы, он не копировать не станет, поскольку не знает что из этого нужно копировать, а что нет. Как результат, в обоих экземплярах теперь указатели ссылаются на одни и те же участки памяти. Далее, вызываем delete [] mapMesh, тот, в свою очередь, вызывает деструктор для каждого экземпляра в массиве, а тот, в свою очередь, удаляет всю выделенную память. Встает вопрос: на что теперь ссылаются указатели из массива temp? Едем дальше, и создаём по новой массив mapMesh, куда копируем всё из массива temp. То есть, теперь данные из mapMesh точно так же ссылаются на уже удалённую деструктором память. Затем вызываем delete [] temp который повторно пытается удалить ту память, на которую ссылаются члены обоих массивов и на которую когда-то ссылался mapMesh до удаления. Вот и ошибка... Можно решить проблему путём написания конструктора копий, можно переопределить оператор =, а лучше всего, на мой взгляд, использовать классы на подобие std::vector, тогда и проблем будет гораздо меньше

16K
30 марта 2006 года
KAPJICOH
4 / / 30.03.2006
Все исправил, большое спасиба.
Реклама на сайте | Обмен ссылками | Ссылки | Экспорт (RSS) | Контакты
Добавить статью | Добавить исходник | Добавить хостинг-провайдера | Добавить сайт в каталог