这些实现会导致内存泄漏吗?

时间:2013-04-24 14:08:06

标签: c++

以下情况是否会导致内存泄漏? 如果是,我该如何解决问题?我应该在Base类中使用指针(即Structure* var)并在析构函数中删除它吗?

如果案例2没有导致内存泄漏,Structure(0,0)会发生什么? 它会立即被创建并被销毁或发生其他事情吗?

案例1:

struct Structure
{
    int a;
    int b;
    Structure() { a=1; b=2; }
    Structure(int num1, int num2) : a(num1), b(num2){}
};

class Base
{
    private:
        Structure var;
    public: 
        Base(Structure structure)
        {
            var = structure;
        }
};

class Derived : public Base
{
    public:
        Derived(bool boolean) : Base(boolean ? *(new Structure(0,0)) : *(new Structure(10,10))){}
};

int main()
{
    Derived derived(true);
}

案例2:

struct Structure
{
    int a;
    int b;
    Structure() { a=1; b=2; }
    Structure(int num1, int num2) : a(num1), b(num2){}
};

class Base
{
    private:
        Structure var;
    public: 
        Base(Structure structure)
        {
            var = structure;
        }
};

class Derived : public Base
{
    public:
        Derived(bool boolean) : Base(boolean ? Structure(0,0) : Structure(10,10)){}
};

int main()
{
    Derived derived(true);
}

3 个答案:

答案 0 :(得分:4)

案例1泄漏是因为您new没有相应的delete

案例2没有泄漏,因为您没有new

答案 1 :(得分:2)

第一种情况非常糟糕:

  Derived(bool boolean) : Base(boolean ? *(new Structure(0,0)) : *(new Structure(10,10))){}
                                           ^^^^                    ^^^

您正在动态分配Structure,但您没有保留指针,因此您无法在其上调用delete,因此您将泄漏内存。第二种情况没有这个问题。

答案 2 :(得分:1)

无论是将true还是false传递给Derived的构造函数,第一种方法都会导致内存泄漏。将在堆上分配一个Structure,然后在分配时由Structure的默认复制构造函数复制

 var = structure;

已执行。

如果你:

  • 使用问题
  • 中建议的指针替换内部var变量类型
  • delete析构函数中的指针
  • Base实施复制构造函数,负责通过var分配重复new
你应该没有任何问题。

struct Structure {
    int a;
    int b;
    Structure() { a=1; b=2; }
    Structure(int num1, int num2) : a(num1), b(num2){}
};

class Base {
    private:
        Structure *var;
    public: 
    Base(Structure *structure) {
        var = structure;
    }
    Base(const Base &b) {
        var = new Structure(*b.var);
    }
    virtual ~Base(){
        delete var;
        var = 0;
    }
};