Исключение, генерируемое при вызове деструктора в postOrderDeletion - PullRequest
1 голос
/ 18 октября 2019

Цель программы - создать объект вызова продукта и добавить этот объект продукта в объект дерева. После добавления шести или семи продуктов основной функции необходимо вызвать деструктор (. ~ BinarySearchTree ()), чтобы удалить все продукты с помощью функции удаления после заказа. Когда я запускаю программу, она выдает исключение (нарушение прав чтения). Реализация ~ BinarySearchTree () и postOrderDeletion находится в BinarySearchTree.cpp

Я попытался удалить продукт, реализовав обычный метод, но это не сработало. Я пытался удалить продукт один за другим: он работал, но в программе необходимо реализовать метод удаления после заказа.

roudct.h

#include <iostream>

#ifndef PRODUCT_H
#define PRODUCT_H
class Product
{
public:
    Product(); // Defaul Constructor
    Product(std::string name, int numberOfItem, double price);
    //Constructor

// Declaring getters
std::string getName() const;
int getNumberOfItem() const;
double getPrice() const;

// Declaring setters
void setName(std::string name);
void setNumberOfItem(int numberOfItem);
void setPrice(double price);

//Utility function
friend std::ostream& operator << (std::ostream& out, const Product& e);
void print();

// Private data members
    private:
    std::string name;
    int numberOfItem;
    double price;
    };
#endif

product.cpp

#include <iostream>
#include "Product.h"

Product::Product() // implementing default constructor
{
    setName("N/A");
    setNumberOfItem(0);
    setPrice(0.0);
}

Product::Product(std::string name, int numberOfItem, double price) // implementing constructor
{
    setName(name);
    setNumberOfItem(numberOfItem);
    setPrice(price);
}

void Product::setName(std::string name) // setting name to this instance
{
    this->name = name;
}

void Product::setNumberOfItem(int numberOfItem) // setting number of items to this instance
{
    this->numberOfItem = numberOfItem;
}

void Product::setPrice(double price) // setting price to this instance
{
    this->price = price;
}

std::string Product::getName() const // returning name of this instance
{
    return name;
}

int Product::getNumberOfItem() const // returning number of item of this instance
{
    return numberOfItem;
}

double Product::getPrice() const // returning price of this instance
{
    return price;
}

Node.h

#include "Product.h"
#ifndef NODE_H
#define NODE_H
class Node
{
public:
    Node()
    {
        left = NULL;
        right = NULL;
    }
private:
    Node* left; // node pointer to left of node
    Node* right; // node pointer to right of node
    Product data; // the product data

    // The binary search tree class can have access to private data members
    friend class BinarySearchTree;
};
#endif // NODE_H

BinarySearchTree.h

#include "Node.h"
#include "Product.h"

#ifndef BINARY_SEARCH_TREE_H
#define BINARY_SEARCH_TREE_H
class BinarySearchTree
{
public:
    BinarySearchTree();
    ~BinarySearchTree();

    void addNode(const Product theProduct);
    void addNode(Node* node, const Product theProduct);

    void postOrderDeletion(Node* node);

    bool isRootEmpty() const;

    //void test();
private:
    Node* root;
};
#endif //BINARY_SEARCH_TREE_H

BinarySearchTree.cpp

#include <iostream>

#include "BinarySearchTree.h"

BinarySearchTree::BinarySearchTree()
{
    root = NULL;
}

BinarySearchTree::~BinarySearchTree()
{
    postOrderDeletion(root);
}

void BinarySearchTree::addNode(const Product theProduct)
{
    if (isRootEmpty())
    {
        Node* newNode = new Node();
        newNode->data = theProduct;
        root = newNode;
    }
    else
    {
        addNode(root, theProduct);
    }

}

void BinarySearchTree::addNode(Node* node, const Product theProduct)
{
    if (theProduct.getName() <= node->data.getName())
    {
        if (node->left)
        {
            addNode(node->left, theProduct);
        }
        else
        {
            Node* newNode = new Node();
            newNode->data = theProduct;
            node->left = newNode;
        }
    }
    else
    {
        if (node->right)
        {
            addNode(node->right, theProduct);
        }
        else
        {
            Node* newNode = new Node();
            newNode->data = theProduct;
            node->right = newNode;
        }
    }
}

void BinarySearchTree::postOrderDeletion(Node* node)
{
    if (node)
    {
        postOrderDeletion(node->left);
        postOrderDeletion(node->right);
        delete node;
    }
}

bool BinarySearchTree::isRootEmpty() const
{
    return (root == NULL);
}

Main.cpp

#include <iostream>

#include "BinarySearchTree.h"

int main()
{
    BinarySearchTree bst;

    Product product1("Napkins", 5, 1.99);
    Product product2("Paper", 10, 0.50);
    Product product3("Chips", 2, 3.45);
    Product product4("Diapers", 10, 7.25);
    Product product5("Video Games", 50, 60.79);
    Product product6("Books", 100, 15.45);
    Product product7("Pens", 123, 4.99);
    Product product8("Pencils", 234, 1.99);
    Product product9("Notebook", 10000, 4.55);
    Product product10("Compositon Notebook", 5000, 2.99);
    Product product11("Cake", 50, 25.00);

    bst.addNode(product5);
    bst.addNode(product9);
    bst.addNode(product3);
    bst.addNode(product7);
    bst.addNode(product8);

    bst.~BinarySearchTree();
    //bst.test();

    return 0;
}

1 Ответ

2 голосов
/ 18 октября 2019

Не делайте этого: bst.~BinarySearchTree(); - просто позвольте bst выйти из области видимости, и деструктор будет вызван автоматически. Теперь он будет вызываться дважды и boom .

Если вы хотите удалить все узлы в дереве, не уничтожая сам объект BinarySearchTree, добавьте общедоступный clear()Метод.

class BinarySearchTree
{
public:
    //...
    void clear();
    //...
};

void BinarySearchTree::clear() {
    postOrderDeletion(root);
}

BinarySearchTree::~BinarySearchTree()
{
    clear(); // use the new clear() method
}

Затем попробуйте это:

#include <iostream>
#include "BinarySearchTree.h"

int main()
{
    { // extra test scope added

        BinarySearchTree bst;

        // add your product nodes
        // and DONT do bst.~BinarySearchTree();

        bst.clear();

        // add new nodes here

    } // calls the destructor that calls clear() and then frees memory here

    std::cout << "still alive\n";

    // or with dynamically allocated objects:
    auto bst = new BinarySearchTree;
    // use it
    delete bst; // calls the destructor and frees memory here

    std::cout << "still alive\n";
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...