Ошибка при освобождении памяти

187
21 марта 2018, 05:27

Добрый день, суть вопроса заключается в том, что когда я пытаюсь очистить память во этом фрагменте кода, срабатывает ошибка -

else {
        RecordBook *next, *prev = listOfStudents;
        current = listOfStudents;
        while (current->next && current->index != pos) {
            prev = current;
            current = current->next;
        }
        next = current->next;
        prev->next = next;
        //!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
        ***//Вот здесь срабатывает ошибка***
        delete current;
        current = NULL;
    }

Вообщем, просидел целый день, так и не понял в чем проблема. Смотрел через дебаггер, он показывает, что указатель указывает на действующую область памяти, так что в чем проблема я не понимаю. Прошу объяснить как можно исправить данную проблему, заранее спасибо!

#include <iostream>
#include <stdio.h>
#include <string>
using namespace std;

class RecordBook {
public:
    void setName(string);
    string getName();
    void setLastName(string);
    string getLastName();
    void setScores(int, int, int, bool, bool, bool);
    void showScores();
private:
    string name;
    string lastName;
    int Math;
    int MathAnalysis;
    int Programming;
    bool English;
    bool PhysEducation;
    bool History;
    //Navigation
    size_t index = 0;
    RecordBook *next = nullptr;
    friend class Group;

};
class Group {
public:
    //Добавить студента
    void addStudent(string, string, int=5, int=5, int=5, bool=true, bool=true, bool=true);
    //Найти студента и вывести оценки
    void findStudent(string);
    //Вставить зачетную книжку в заданный индекс
    void insert(RecordBook &, size_t = 0);
    //Удалить зачетную книжку по заданному индексу
    void erase(size_t = 0);
private:
    //Динамический список студентов, который указывает на последнего студента
    RecordBook *listOfStudents;
    //Количество студентов
    size_t countOfElements = 0;
    //Создать новый узел для студента в динамическом списке
    void createOfNode(RecordBook &);
    //Обновить индексы динамического списка
    void updateOfIndex();
} mx101;
int main() {
    setlocale(0, "");
    mx101.addStudent("Al", "As");
    mx101.addStudent("Petya", "Petrov");
    RecordBook student;
    student.setName("vasya");
    student.setLastName("XXX");
    student.setScores(2, 3, 4, 1, 1, 0);
    mx101.insert(student, 1);
    mx101.erase(1);
    return 0;
}
void RecordBook::setName(string name1) {
    name = name1;
}
string RecordBook::getName() {
    return name;
}
void RecordBook::setLastName(string lastName1) {
    lastName = lastName1;
}
string RecordBook::getLastName() {
    return lastName;
}
void RecordBook::setScores(int M, int MA, int pr, bool En, bool Ph, bool Hi) {
    Math = M;
    MathAnalysis = MA;
    Programming = pr;
    English = En;
    PhysEducation = Ph;
    History = Hi;
}
void RecordBook::showScores() {
    printf("Name: %s, Last Name: %s\n", name.c_str(), lastName.c_str());
    printf("Math: %d, Math analysis: %d, Programming: %d\n", Math, MathAnalysis, Programming);
    printf(English ? "English: passed\n" : "English: didn't passed\n");
    printf(PhysEducation ? "PhysEducation: passed\n" : "PhysEducation didn't passed\n");
    printf(History ? "History: passed\n" : "History: didn't passed\n");
    cout << endl;
}
void Group::addStudent(string name, string lastName, int a, int b, int c, bool d, bool e, bool f) {
    RecordBook student;
    student.setName(name);
    student.setLastName(lastName);
    student.setScores(a, b, c, d, e, f);
    createOfNode(student);
}
void Group::createOfNode(RecordBook &elem) {
    RecordBook *current = new RecordBook;
    if (countOfElements == 0) {
        *current = elem;
        current->next = nullptr;
        current->index = countOfElements++;
        listOfStudents = current;
    }
    else {
        *current = elem;
        current->index = countOfElements++;
        current->next = listOfStudents;
        listOfStudents = current;
    }
}
void Group::findStudent(string str) {
    RecordBook *current = listOfStudents;
    do {
        if (!current->getName().compare(str) || !current->getLastName().compare(str)) {
            current->showScores();
            return;
        }
        else {
            current = current->next;
        }
    } while (current);
    cout << "Ничего не найдено" << endl;
}
void Group::insert(RecordBook &elem, size_t pos) {
    if (pos < 0 || pos > countOfElements) cout << "Неверный индекс" << endl;
    else {
        RecordBook *current = NULL;
        if (pos == 0) {
            current = listOfStudents;
            while (current->next) {
                current = current->next;
            }
            current->next = &elem;
        }
        else if (pos == countOfElements) {
            current = new RecordBook;
            current = &elem;
            current->next = listOfStudents;
            listOfStudents = current;
        }
        else {
            RecordBook *next = NULL;
            current = listOfStudents;
            while (current->next && current->index != pos) {
                current = current->next;
            }
            RecordBook *item = new RecordBook;
            next = current->next;
            item = &elem;
            item->next = next;
            current->next = item;
        }
        countOfElements++;
        updateOfIndex();
    }
}
void Group::erase(size_t pos) {
    if (pos < 0 || pos > countOfElements - 1) cout << "Неверный индекс" << endl;
    else {
        RecordBook *current;
        if (pos == 0) {
            current = listOfStudents;
            while (current->next->next) {
                current = current->next;
            }
            delete current->next;
            current->next = NULL;
        }
        else if (pos == countOfElements - 1) {
            current = listOfStudents;
            listOfStudents = listOfStudents->next;
            delete current;
            current = NULL;
        }
        else {
            RecordBook *next, *prev = listOfStudents;
            current = listOfStudents;
            while (current->next && current->index != pos) {
                prev = current;
                current = current->next;
            }
            next = current->next;
            prev->next = next;
            //!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
            ***//Вот здесь срабатывает ошибка***
            delete current;
            current = NULL;
        }

    }
}
void Group::updateOfIndex() {
    RecordBook *current = listOfStudents;
    size_t acc = countOfElements - 1;
    while (current->next) {
        current->index = acc--;
        current = current->next;
    }
}
Answer 1

Вы добавляете в динамический список объект RecordBook student; на стеке. Соответственно попытка delete current; приводит к неопределенному поведению. Кроме того, поле RecordBook *listOfStudents; остается неинициализированным.

READ ALSO
Ввод элементов стека через консоль

Ввод элементов стека через консоль

Как реализовать ввод элементов стека не статичными данными, а с помощью ввода через консоль? Ну, те

201
Как перенести не вмещающийся текст

Как перенести не вмещающийся текст

Как перенести на новую строчку текст, который выходит за пределы нужной области? Или не больше 35 символов в строчке, если больше то на новую...

261
NoSuchMethodError в gradle проекте

NoSuchMethodError в gradle проекте

При выполнении следующего кода возникает ошибка javalang

196
Сдвиг по временной зоне (TimeZone)

Сдвиг по временной зоне (TimeZone)

Стала задача установить дату, переданную клиентом, в его временную зонуС помощью TimeZone

199