【问题标题】:Memory Leak from Referenced Pointer引用指针的内存泄漏
【发布时间】:2018-01-20 21:36:30
【问题描述】:

我正在学习引用指针和内存泄漏。

我创建了一个方法,它接收指向 NodeData 的指针,创建一个包含 NodeData、左指针和右指针的节点,并根据其值插入它。我正在使用引用指针来遍历我的树。每次我声明一个新的 Node 对象并超出范围时,都会发生内存泄漏。

我以为既然指针引用指向了对象,它就没有消失。我的程序运行良好,但是当我使用 valgrind 时出现错误。

我已经以多种方式编写了此方法,但找不到修复它的方法。我贴出了我写过的最简洁的方法。

bool BinTree::insert(NodeData* s) {
    Node* currentPtr = root;
    bool insert = insertHelper(s, currentPtr);
    return insert;
};

bool BinTree::insertHelper(NodeData* s, Node*& currentPtr) {
    if (currentPtr == NULL) {
        Node* newNodePtr = new Node;
        newNodePtr->data = s;
        newNodePtr->left = NULL;
        newNodePtr->right = NULL;
        currentPtr = newNodePtr;
        return true;
    } else if (*s == *currentPtr->data) {
        return false;
    } else if (*s < (*currentPtr->data)) {
        return insertHelper(s, currentPtr->left);
    } else {
        return insertHelper(s, currentPtr->right);
    }
}

由于类似的错误,我的程序中出现大量内存泄漏。

或者,有人能解释一下指针引用背后的概念,或者了解更多关于它的方法吗?

这个方法使用的方法:

void buildTree(BinTree& T, ifstream& infile) {                                         
    string s;                                                                                                                                                                
for (;;) {                                                                         
    infile >> s;                                                                   
    cout << s << ' ';                                                              
    if (s == "$$") break;                // at end of one line                     
    if (infile.eof()) break;             // no more lines of data                  
    NodeData* ptr = new NodeData(s);     // NodeData constructor takes string      
    // would do a setData if there were more than a string                         

    bool success = T.insert(ptr);                                                  
    if (!success)                                                                  
        delete ptr;                       // duplicate case, not inserted          
}
}

【问题讨论】:

  • 究竟显示了什么错误?如何删除树的节点?当您忘记释放内存(使用 orerator delete)时,通常会发生内存泄漏
  • insert() 内,变量currentPtr 具有自动存储持续时间,因此在函数返回时不再存在。让它指向某个东西(通过将它传递给insertHelper(),这在某些情况下会在您的代码中改变它)并不会改变它。
  • Sandro,我们的任务不包括删除操作符。我将包括我的教授编写的使用插入的方法。
  • Peter,如果我只使用 root 作为参数而不是 currentPtr,我会得到更多的内存泄漏。
  • 第一个目标是让程序正常工作,如果程序停止执行它应该做的事情,更少的内存泄漏并不是一件好事。

标签: c++ pointers memory-leaks reference


【解决方案1】:

你可能会有更多的运气

bool BinTree::insert(NodeData* s) {
    bool insert = insertHelper(s, root);
    return insert;
};

您的代码修改了一个局部变量,而不是根。

如果要修改根目录,则需要对根目录的引用,而不是对具有根副本的局部变量的引用。

【讨论】:

  • 我也这么认为。我最初使用 root 尝试过,但使用 root 会导致更多的内存泄漏。我的泄漏发生在:“Node *newNodePtr = new Node”
  • 需要查看完整的程序才能知道泄漏的位置。
  • 约翰,我已经包含了使用插入方法的方法。我还应该包括什么?
  • 一个完整的程序,它不一定是整个程序,但它必须是完整的。想一想,当您看不到完整的程序时,如何可靠地看到内存泄漏?内存可以在未包含的程序的一部分中释放。
  • 我把你所说的考虑到了约翰,到目前为止,我似乎已经解决了这个问题。在我的析构函数中,我删除了 NodeData 和指针,但没有删除 Node 对象本身。我知道这可能是一个新手错误,如果不是边缘菜鸟的话。非常感谢您抽出时间来帮助我!
猜你喜欢
  • 1970-01-01
  • 2013-11-30
  • 1970-01-01
  • 1970-01-01
  • 2013-10-31
  • 2015-12-15
  • 1970-01-01
  • 2017-11-30
  • 2011-07-09
相关资源
最近更新 更多