简体   繁体   English

删除对象时崩溃

[英]Crashing when objects are deleted

It's crashing at the very end of the main() function where it needs to delete the starters objects. 它在需要删除starters对象的main()函数的最后崩溃了。 The error message that pops up when I run the program says: Debug assertion failed! 运行程序时弹出的错误消息显示:调试断言失败! Expression: _BLOCK_IS_VALID(pHead->nBlockUse). 表达式:_BLOCK_IS_VALID(pHead-> nBlockUse)。 How do i fix it from crashing when deleting the starters objects? 如何删除启动程序对象时避免崩溃?

#include <iostream>
#include <fstream>
#include "olympic.h"

using namespace std;

ofstream csis;

int main() {
const int lanes = 4;
Ranker rank(lanes);

csis.open("csis.txt");

// First make a list of names and lane assignments.
Competitor* starters[lanes];

starters[0] = new Competitor("EmmyLou Harris", 1);
starters[1] = new Competitor("Nanci Griffith", 2);
starters[2] = new Competitor("Bonnie Raitt", 3);
starters[3] = new Competitor("Joni Mitchell", 4);

// The race is run; now assign a time to each person.
starters[0]->setTime((float)12.0);
starters[1]->setTime((float)12.8);
starters[2]->setTime((float)11.0);
starters[3]->setTime((float)10.3);

// Put everyone into the ranker.
for (int i = 0; i < lanes; i++)
    rank.addList(starters[i]);

// Now print out the list to make sure its right.
cout << "Competitors by lane are:" << endl;
csis << "Competitors by lane are:" << endl;
for (int i = 1; i <= lanes; i++)
    rank.getLane(i)->print();

// Finally, show how they finished.
cout << "Rankings by finish are:" << endl;
csis << "Rankings by finish are:" << endl;
for (int i = 1; i <= lanes; i++)
    rank.getFinish(i)->print();
for (int i = 0; i < lanes; i++)
    delete starters[i];

csis.close();

} }

ranker.cpp: ranker.cpp:

#include "ranker.h"
#include "competitor.h"
#include <stdlib.h>

Ranker::Ranker(int lanes) {
athlete = new Competitor*[lanes]; 
numAthletes = 0;
maxAthletes = lanes;
}

int Ranker::addList(Competitor* starter) {
if (numAthletes < maxAthletes && starter != NULL) {
    athlete[numAthletes] = starter;
    numAthletes++;

    return numAthletes;
}
else
    return 0;
}

Competitor* Ranker::getLane(int lane) {
for (int i = 0; i < numAthletes; i++) {
    if (athlete[i]->getLane() == lane) {
        return athlete[i];
    }
}
return NULL;
}


Competitor* Ranker::getFinish(int position) {
switch(position) {
    case 1:
        return athlete[3];
        break;
    case 2:
        return athlete[2];
        break;
    case 3:
        return athlete[1];
        break;
    case 4:
        return athlete[0];
        break;
}
return NULL;
}

int Ranker::getFilled() {
return numAthletes;
}

Ranker::~Ranker() {
delete [] athlete;
}

competitor.h: 竞争对手:

#ifndef _COMPETITOR_H
#define _COMPETITOR_H

 class Competitor {
     private:
        char* name;
        int lane;
        double time;
     public:
        Competitor(char* inputName, int inputLane);
        Competitor();
        void setTime(double inputTime);
        char* getName();
        int Competitor::getLane();
        double getTime();
        void print();
       ~Competitor();
    };

    #endif

competitor.cpp: competitor.cpp:

#include "competitor.h"
#include <string>
#include <iostream>
#include <iomanip>

using namespace std;


 Competitor::Competitor(char* inputName, int inputLane) {
name = inputName;
lane = inputLane;
}

Competitor::Competitor() {
name = 0;
lane = 0;
time = 0;
}

 void Competitor::setTime(double inputTime) {
time = inputTime;
}

char* Competitor::getName() {
return name;
}

int Competitor::getLane() {
return lane;
 }

 double Competitor::getTime() {
return time;
}

void Competitor::print() {
cout << setw(20) << name << setw(20) << lane << setw(20) << setprecision(4) << time        << endl;
}

Competitor::~Competitor() {
delete [] name;
}

Call stack: 调用堆栈:

before crash: http://i.imgur.com/d4sKbKV.png after crash: http://i.imgur.com/C5cXth9.png 崩溃前: http : //i.imgur.com/d4sKbKV.png崩溃后: http : //i.imgur.com/C5cXth9.png

After you've added Competitor class, it seems the problem is that you delete its name in Competitor's destructor. 添加Competitor类后,似乎出现的问题是您在Competitor的析构函数中删除了它的名称。 But you assign it from string literal which can't really be deleted. 但是您是从不能真正删除的字符串文字中分配它的。 I'm sure the stack trace leading to assertion will prove that. 我确信导致断言的堆栈跟踪将证明这一点。

One way of solving the problem would be using std::string to store the name. 解决问题的一种方法是使用std :: string来存储名称。

Problem is when deleting the char* value on destructor, which is assigned with const char instead new char. 问题是删除析构函数上的char *值时,该值由const char而不是new char分配。 So i have slightly changed the constructor to copy the const char to new char. 所以我稍微改变了构造函数,将const char复制到new char。

Competitor::Competitor(char* inputName, int charlen, int inputLane) 
{
name = new char[charlen + 1];
memcpy(name , inputName, charlen );
name [charlen] = '\0'; 
lane = inputLane;
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM