c++析构函数内存泄漏

C++ destructor memory leak

本文关键字:泄漏 内存 析构函数 c++      更新时间:2023-10-16

关于正确处理析构函数的相对简单的问题…

首先我有一个像这样的类:

class Foo {
public:
    ReleaseObjects() {
        for (std::map<size_t, Object*>::iterator iter = objects.begin(); iter != objects.end(); iter++) {
            delete (*iter).second;
        }
        objects.clear();
    }
private:
    std::map<size_t,Object*> objects;
}

因此该函数只是删除使用'new'创建的对象。问题是对象类:

class Bar : public Object {
public:
    Bar() {
        baz = new Baz();
    }
    ~Bar() { delete baz; }
private:
    Baz* baz;
}

如果我添加一个类型Baz对象到Foo,然后尝试ReleaseObjects(),我得到一个内存泄漏(valgrind)。问题指向baz被泄露,我猜这意味着bar中的析构函数永远不会被调用?所以我想知道的是,当试图销毁该对象时,如何调用Bar析构函数(我不能改变Bar类,但我可以改变Foo)。

编辑:哦,抱歉语法错误。无论如何,感谢所有的回复,愚蠢的我忘了在我的Baz类中实现一个适当的析构函数!哦,Baz实际上是一个模板类,但我认为Baz与我的问题无关,问题是Bar中的析构函数没有被调用……我错了,问题出在巴兹身上。但是再次感谢你,我想我已经明白了!

你必须确保你的析构函数是虚的,以便调用适当的派生析构函数。

class Object {
 . . .
 virtual ~Object()
 . . .
};

我不完全理解您的场景,但是由于您有公共继承,您可能需要虚拟析构函数。特别是,基类(Object)需要一个虚析构函数。

请注意,给定的代码无法编译。new操作符返回指针,因此baz必须是指针。

你应该始终使用智能指针。这些类型的行为类似指针,但会自动释放内存,并且不需要任何此类函数。它们可以避免各种讨厌的bug——可能包括这个bug,如果你使用shared_ptr<Bar>并把它扔下去的话。

如果你想用c++编写重要的软件,你必须知道并理解智能指针。