目录

C++ Dynamic Memory

很好地理解动态内存如何在C ++中真正起作用对于成为一名优秀的C ++程序员至关重要。 C ++程序中的内存分为两部分 -

  • The stack - 在函数内声明的所有变量将从堆栈中占用内存。

  • The heap - 这是程序未使用的内存,可用于在程序运行时动态分配内存。

很多时候,您事先并不知道在特定变量中存储特定信息需要多少内存,并且可以在运行时确定所需内存的大小。

您可以使用C ++中的特殊运算符在堆内的运行时为给定类型的变量分配内存,该运算符返回分配的空间的地址。 此运算符称为new运算符。

如果您不再需要动态分配的内存,可以使用delete运算符,它取消分配以前由new运算符分配的内存。

new和delete运算符

以下通用语法使用new运算符为任何数据类型动态分配内存。

new data-type;

这里, data-type可以是任何内置数据类型,包括数组或任何用户定义的数据类型包括类或结构。 让我们从内置数据类型开始。 例如,我们可以定义一个指向double类型的指针,然后请求在执行时分配内存。 我们可以使用new运算符并使用以下语句执行此操作 -

double* pvalue  = NULL; // Pointer initialized with null
pvalue  = new double;   // Request memory for the variable

如果免费商店已用完,则可能尚未成功分配内存。 因此,最好检查新运算符是否返回NULL指针并采取以下相应的操作 -

double* pvalue  = NULL;
if( !(pvalue  = new double )) {
   cout << "Error: out of memory." <<endl;
   exit(1);
}

来自C的malloc()函数仍然存在于C ++中,但建议避免使用malloc()函数。 new over malloc()的主要优点是new不只是分配内存,而是构造C ++主要目的的对象。

在任何时候,当您感觉不再需要动态分配的变量时,您可以使用'delete'运算符释放它在免费存储中占用的内存,如下所示 -

delete pvalue;        // Release memory pointed to by pvalue

让我们将上述概念放在上面,并形成以下示例,以显示“新”和“删除”的工作原理 -

#include <iostream>
using namespace std;
int main () {
   double* pvalue  = NULL; // Pointer initialized with null
   pvalue  = new double;   // Request memory for the variable
   *pvalue = 29494.99;     // Store value at allocated address
   cout << "Value of pvalue : " << *pvalue << endl;
   delete pvalue;         // free up the memory.
   return 0;
}

如果我们编译并运行上面的代码,这将产生以下结果 -

Value of pvalue : 29495

数组的动态内存分配

考虑您要为字符数组分配内存,即20个字符的字符串。 使用上面我们使用的相同语法,我们可以动态分配内存,如下所示。

char* pvalue  = NULL;         // Pointer initialized with null
pvalue  = new char[20];       // Request memory for the variable

要删除我们刚创建的数组,语句将如下所示 -

delete [] pvalue;             // Delete array pointed to by pvalue

遵循new运算符的类似通用语法,您可以按如下方式为多维数组分配 -

double** pvalue  = NULL;      // Pointer initialized with null 
pvalue  = new double [3][4];  // Allocate memory for a 3x4 array 

但是,释放多维数组内存的语法仍然与上面相同 -

delete [] pvalue;            // Delete array pointed to by pvalue

对象的动态内存分配

对象与简单数据类型没有区别。 例如,考虑以下代码,我们将使用对象数组来阐明概念 -

#include <iostream>
using namespace std;
class Box {
   public:
      Box() { 
         cout << "Constructor called!" <<endl; 
      }
      ~Box() { 
         cout << "Destructor called!" <<endl; 
      }
};
int main() {
   Box* myBoxArray = new Box[4];
   delete [] myBoxArray; // Delete array
   return 0;
}

如果你要分配一个包含四个Box对象的数组,那么Simple构造函数将被调用四次,同样在删除这些对象时,析构函数也会被调用相同的次数。

如果我们编译并运行上面的代码,这将产生以下结果 -

Constructor called!
Constructor called!
Constructor called!
Constructor called!
Destructor called!
Destructor called!
Destructor called!
Destructor called!
C++ Namespaces.下一篇>
↑回到顶部↑
WIKI教程 @2018