C++ 释放内存(如果可能)

C++ 释放内存(如果可能),c++,C++,我可以释放用于分配对象的内存吗?如果是,我怎么做 class CRectangle { int width, height; public: CRectangle (int,int); ~CRectangle (); int area () { return (width * height); } }; CRectangle::CRectangle (int a, int b) { width = a; height =

我可以释放用于分配对象的内存吗?如果是,我怎么做

class CRectangle {
    int width, height;
public:
    CRectangle (int,int);
    ~CRectangle ();
    int area () {
        return (width * height);
    }
};

CRectangle::CRectangle (int a, int b) {
    width = a;
    height = b;
}

CRectangle::~CRectangle () {
    // Do something here
}
如果我使用动态内存分配,它将是:

   class CRectangle {
        int *width, *height;
    public:
        CRectangle (int,int);
        ~CRectangle ();
        int area () {
            return (*width * *height);
        }
    };

    CRectangle::CRectangle (int a, int b) {
        width = new int;
        height = new int;
        *width = a;
        *height = b;

    }

    CRectangle::~CRectangle () {
        delete width
        delete height
    }

它们有相同的输出,那么使用动态内存分配有什么好处呢?

要回答这个问题,没有。所有成员都会在对象实例化时自动分配。唯一需要担心释放内存的情况是在动态分配的情况下(因为自动内存在超出范围之前无法释放)。以这两个INT为例:

int a; //automatic allocation at point of declaration, will exist until it falls out of scope
int *a = new int; //dynamic allocation, exists until deleted. Falling out of scope without releasing memory can cause a memory leak

现在,如果您正在动态地分配对象,那么您可以释放内存,但这是在您的类之外完成的

CRectangle *rect;
rect = new CRectangle; //dynamically allocated

//....

delete rect; //free memory allocated by rect

答案是否定的。对象实例化时,会自动分配所有成员。唯一需要担心释放内存的情况是在动态分配的情况下(因为自动内存在超出范围之前无法释放)。以这两个INT为例:

int a; //automatic allocation at point of declaration, will exist until it falls out of scope
int *a = new int; //dynamic allocation, exists until deleted. Falling out of scope without releasing memory can cause a memory leak

现在,如果您正在动态地分配对象,那么您可以释放内存,但这是在您的类之外完成的

CRectangle *rect;
rect = new CRectangle; //dynamically allocated

//....

delete rect; //free memory allocated by rect

在您设计的类中,您不需要在析构函数中执行任何操作

这没关系:

CRectangle::~CRectangle () {
}

在您设计的类中,您不需要在析构函数中执行任何操作

这没关系:

CRectangle::~CRectangle () {
}

在您的特定示例中,这两种方法在技术上都是正确的,在析构函数中不需要做更多的工作

在第二个例子中,这绝对没有好处,事实上这是在浪费内存,因为内存分配中存在开销。最小的此类开销是12字节+分配本身-在您的情况下,如果我们假设
int
为4字节(这是常见的,但也有其他选择),则总共是16字节

当对象的大小不同时(您的大小始终为一个
int
)[并且最大大小大于分配内存本身的预期开销]或对象的大小是可选的[并且大于分配对象的预期开销],分配对象是有益的

例如,假设我们让你的
CRectangle
为每一个大小单位持有一个
CCell
对象(例如,它可能是某种游戏中每个单元格的内容)。现在,如果我们也想象一个矩形可以是任意大小的,从1 x 1到每边几千,我们不想做一个静态的二维数组,每个维度几千,对吗?所以我们必须动态地分配它。出于讨论的目的,我将分配一个大数组
width*height
,因为这是我们需要的大小。人们可以考虑做二维分配,但这会使代码变得更复杂。 下面是它的样子:

class CRectangle {
    int width, height;
    CCell* cellArray;
public:
    CRectangle (int,int);
    ~CRectangle ();
    int area () {
        return (width * height);
    }
};

CRectangle::CRectangle (int a, int b) {
    width = a;
    height = b;
    cellArray = new CCell[width * height];
}

CRectangle::~CRectangle () {
    delete [] cellArray;
}

在您的特定示例中,这两种方法在技术上都是正确的,在析构函数中不需要做更多的工作

在第二个例子中,这绝对没有好处,事实上这是在浪费内存,因为内存分配中存在开销。最小的此类开销是12字节+分配本身-在您的情况下,如果我们假设
int
为4字节(这是常见的,但也有其他选择),则总共是16字节

当对象的大小不同时(您的大小始终为一个
int
)[并且最大大小大于分配内存本身的预期开销]或对象的大小是可选的[并且大于分配对象的预期开销],分配对象是有益的

例如,假设我们让你的
CRectangle
为每一个大小单位持有一个
CCell
对象(例如,它可能是某种游戏中每个单元格的内容)。现在,如果我们也想象一个矩形可以是任意大小的,从1 x 1到每边几千,我们不想做一个静态的二维数组,每个维度几千,对吗?所以我们必须动态地分配它。出于讨论的目的,我将分配一个大数组
width*height
,因为这是我们需要的大小。人们可以考虑做二维分配,但这会使代码变得更复杂。 下面是它的样子:

class CRectangle {
    int width, height;
    CCell* cellArray;
public:
    CRectangle (int,int);
    ~CRectangle ();
    int area () {
        return (width * height);
    }
};

CRectangle::CRectangle (int a, int b) {
    width = a;
    height = b;
    cellArray = new CCell[width * height];
}

CRectangle::~CRectangle () {
    delete [] cellArray;
}

代码中没有内存分配,除了对象本身的大小。代码中没有内存分配,除了对象本身的大小。动态分配和自动分配之间有什么大的区别吗?因为在这种情况下,它们可以达到相同的输出?内存方面,非常不同。就对象而言,它就像一个自动分配的对象。您可能想了解动态分配及其用途:实际上,如果您正在设计智能指针,您只需担心释放内存。所有其他代码应该只使用已经知道何时以及如何释放内存的智能指针。动态分配和自动分配之间有什么大的区别吗?因为在这种情况下,它们可以达到相同的输出?内存方面,非常不同。就对象而言,它就像一个自动分配的对象。您可能想了解动态分配及其用途:实际上,如果您正在设计智能指针,您只需担心释放内存。所有其他代码应该只使用已经知道何时以及如何释放内存的智能指针。-1不正确。如果有人在运行时通过“新建”创建对象,则始终需要删除这些对象。在这种情况下,在析构函数中。@Rvdk:类的析构函数不能删除自身。这将导致无限递归。不,我说的是通过new在CRectangle中创建的宽度和高度,它们应该在析构函数中删除。CRectangle本身的创建应该在它创建的地方。啊,但是现在你在谈论differ