二叉搜索树的赋值运算符中的内存泄漏

时间:2016-01-30 06:10:12

标签: c++ memory memory-leaks variable-assignment assignment-operator

所以我似乎无法找出为什么我会泄漏记忆,有人可以帮忙吗?我用operator=:

实现了一个二叉搜索树
BinTree& BinTree::operator=(const BinTree &other)
{
    if (other.root == NULL)
        root = NULL;
    else
    {
        copyHelper(root, other.root);
    }
    return *this;

}

copyHelper:

void BinTree::copyHelper(Node *&current, const Node *other)
{
    if (other == NULL)
        current = NULL;
    else
    {
        current = new Node;
        current->data = other->data;
        copyHelper(current->left, other->left);
        copyHelper(current->right, other->right);
    }   
}

我知道current = new Node;是泄密发生的地方,但如果我在该行之前尝试delete current;,我的程序会崩溃。

这是我的析构函数:

BinTree::~BinTree()
{
    destroyRecursive(root);
}

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

2 个答案:

答案 0 :(得分:1)

由于您使用原始指针,因此必须手动删除已分配的内存。将current设置为NULL

时,会泄漏内存
void BinTree::copyHelper(Node *&current, const Node *other)
{
    if (other == NULL)
    {
        delete current;    // w/o this line next
        current = NULL;    // will cause memory leak (if not managed somewhere else)
    }
    else
    {
        current = new Node;
        current->data = other->data;
        copyHelper(current->left, other->left);
        copyHelper(current->right, other->right);
    }   
}

答案 1 :(得分:0)

代码结构不佳。 C ++为您提供了执行此操作的所有工具,但您很少或根本没有优势。您需要删除当前树的 root 在运算符函数中,然后 copy-construct 新节点;你需要修复你的析构函数。

  1. 递归复制助手应该是Node类中的复制构造函数:

    Node::Node(const Node &other) : left(0), right(0)
    {
        this->data = other.data; // This must be a deep copy
        if (other.left)
            this->left = new Node(other.left);
        if (other.right)
            this->right = new Node(other.right);
    }
    
  2. 这由BinTree赋值运算符调用:

    BinTree& BinTree::operator=(const BinTree &other)
    {
        delete root;
        this->root = 0;
        if (other.root)
            this->root = new Node(other.root);
        return *this;
    }
    
  3. 您不需要递归销毁方法。 BinTree析构函数中只需要delete root;Node的析构函数:

    Node::~Node()
    {
        delete left;
        delete right;
    }
    
  4. data的复制必须是深层复制。例如,如果它是C字符串,请在strdup(),的析构函数中使用free()Node。如果它是一个类,那么该类必须有一个赋值运算符。