在base析构函数之前调用派生的析构函数会导致问题

时间:2011-01-10 18:58:38

标签: c++

这是我的问题:

我的基类有一个构造函数,它接受一个类指针,如果该指针为NULL,它知道自己实例并维护它。

问题是,在基础析构函数中,我必须用私有的base取消注册该指针。所以当我尝试在基础析构函数中调用类指针并且派生维护它时,它已经被释放了。这会导致问题。我该怎么办?

由于

5 个答案:

答案 0 :(得分:1)

如果基类为指针创建实例,为什么它 free 呢?是否有什么阻止你将自由移动到基础析构函数中?

总是最好在谁做什么方面保持一致,在一定程度的等级 - 在多个层次结构中分担相同的责任肯定会导致诸如此类的问题。更不用说,如果你想创建另一个继承自base的类,你也必须在新类中重新实现这个管理,创建代码重复。

答案 1 :(得分:0)

继承的构造函数和析构函数的顺序是相反的;基础构造函数在其任何派生构造函数之前调用。删除后,会发生反转 - 首先删除派生类。

要解决您的问题,基础析构函数是否可以测试其私有实例是否不是NULL

答案 2 :(得分:0)

从你的描述我收集到有时派生类将负责这个指针,有时候基类会是。我能想到的最简单的解决方案是在基类中添加一个布尔值,以便跟踪谁拥有该对象。如果基类已初始化指针,则将布尔值设置为true。然后你的析构函数可以检查谁拥有该对象,反过来是否应该清理它。

更好的解决方案是使用boost:shared_ptr。这是一个引用计数指针抽象,它将在最后一个引用超出范围时自动清理对象。通过这种抽象,您通常不必担心谁会释放您的指针。

答案 3 :(得分:0)

基类可以实现一个protected成员函数来进行清理,然后派生的析构函数可以在销毁资源之前调用这个帮助函数。

答案 4 :(得分:0)

如果构造函数分配内存,则相应的析构函数负责释放它。如果你有条件地分配内存,那么你需要有条件地释放它。布尔标志可以帮助您确定是否发生了分配。

另一种解决方案是使用引用计数。在分配时,引用计数应为1.如果另一个类对该对象感兴趣,则它通过增加引用计数来保留指针。如果某个类不再对该对象感兴趣,则会减少引用计数。当计数器达到0时,必须删除该对象。 shared_ptr是一个标准的C ++引用计数自动指针实现,它在复杂的混合所有权情况下非常有效。