在没有虚拟析构函数的情况下删除基类指针时,会导致内存泄漏吗? [英] Would it lead to memory leak when delete base class pointer without virtual destructor?

查看:220
本文介绍了在没有虚拟析构函数的情况下删除基类指针时,会导致内存泄漏吗?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

以下是解释虚拟析构函数的示例.(请参见 http://www.geeksforgeeks .org/g-fact-37/) 我根据该示例修改了代码,并对内存泄漏有疑问.

Here is an example for explaining virtual destructor.(see http://www.geeksforgeeks.org/g-fact-37/) I modify the code based on that example, and have a question about memory leak.

假设基类的变量为int num,派生类的变量为float money.

Suppose Base class has a variable of int num, Derived class has variable of float money.

当调用delete base_ptr;时,由于基类的析构函数是虚拟的,因此应先调用~derived(),然后再调用~Base().

When delete base_ptr;is called, since destructor of base class is virtual, ~derived() should be called first and then ~Base().

我的问题是函数删除是否可以足够聪明,以便它释放为int num(基类)和float money(派生类)分配的内存?

My question is "can function delete is smart enough so that it would free the memory allocated for both int num(Base Class) and float money(Derived Class)?

我认为base_ptr是Base *类型的指针,因此它可能仅释放Base类所需的内存量.但是,即使base_ptr指向Base类的类型,似乎int和float都将被释放.如果是这样,如果我们将~Base()设为非虚拟析构函数,是否会导致内存泄漏?使用~Base()的非虚拟析构函数,我们会错过~Derived()的调用.因为在基类和派生类中都没有动态分配"任何东西,所以~Derived()似乎根本没有释放任何内存,而delete的功能将同时释放int numfloat money的内存.

I think base_ptr is the pointer of type Base*, so it might only free the amount of memory needed for Base class. However, it seems that both int and float would be freed even if base_ptr is pointing type of Base class. If it is the case, would it lead to memory leak if we make ~Base() a non-virtual destructor? With a non-virtual destructor of ~Base(), we would miss the call of ~Derived(). Because nothing is dynamically allocated "within" both Base Class and Derived Class, it seems that ~Derived() does not actually free any memory at all, and function of delete would free both memory of int num and float money.

#include <iostream>
using namespace std;

class Base {
public:
    int num;

 Base(int n):num(n){
    cout<<"Base::Constructor\n";
 }
    virtual ~Base(){
    cout<<"Base::Destructor\n";
 }
};

class Derived : public Base {
private:
  float money;
public:
 Derived(int n, float m):Base(n),money(m){
    cout<<"Derived::Constructor\n";
 }
 ~Derived(){
    cout<<"Derived::destructor\n";
 }
};



int main() {
    Base *base_ptr = new Derived(1,200.0);
    delete base_ptr;
    return 0;
}

推荐答案

您所描述的是未定义行为,这意味着任何令人讨厌的东西都可能出错,而不仅仅是内存泄漏.

What you are describing is Undefined Behavior, which means any nasty stuff could go wrong, not just memory leaks.

但是在实践中,如果继承不是虚拟的,则派生类没有其他基类,并且派生类没有具有非平凡析构函数的成员,则可能会调用Base::~Base()析构函数,然后operator delete在指针上调用. operator delete(void*)函数只需获取一个指针并释放它所指向的所有内存,因此那里没有内存泄漏".

But in practice, if the inheritance is not virtual, the derived class has no other base classes, and the derived class has no members with non-trivial destructors, you'll probably get the Base::~Base() destructor invoked and then operator delete called on the pointer. The operator delete(void*) function just takes a pointer and frees up all the memory it pointed at, so no "memory leak" there.

这篇关于在没有虚拟析构函数的情况下删除基类指针时,会导致内存泄漏吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆