Memoria dinámica C ++

Una buena comprensión de cómo funciona realmente la memoria dinámica en C ++ es esencial para convertirse en un buen programador de C ++. La memoria en su programa C ++ se divide en dos partes:

  • The stack - Todas las variables declaradas dentro de la función ocuparán memoria de la pila.

  • The heap - Esta es la memoria no utilizada del programa y se puede usar para asignar la memoria de forma dinámica cuando se ejecuta el programa.

Muchas veces, no sabe de antemano cuánta memoria necesitará para almacenar información particular en una variable definida y el tamaño de la memoria requerida se puede determinar en tiempo de ejecución.

Puede asignar memoria en tiempo de ejecución dentro del montón para la variable de un tipo dado usando un operador especial en C ++ que devuelve la dirección del espacio asignado. Este operador se llamanew operador.

Si ya no necesita memoria asignada dinámicamente, puede usar delete operador, que desasigna la memoria que previamente asignó el nuevo operador.

nuevos y eliminar operadores

Existe la siguiente sintaxis genérica para usar new operador para asignar memoria dinámicamente para cualquier tipo de datos.

new data-type;

Aquí, data-typepodría ser cualquier tipo de datos incorporado, incluida una matriz, o cualquier tipo de datos definido por el usuario que incluya clase o estructura. Comencemos con los tipos de datos integrados. Por ejemplo, podemos definir un puntero para escribir double y luego solicitar que se asigne la memoria en el momento de la ejecución. Podemos hacer esto usando elnew operador con las siguientes declaraciones:

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

Es posible que la memoria no se haya asignado correctamente si se ha agotado el almacenamiento libre. Por lo tanto, es una buena práctica verificar si el nuevo operador está devolviendo un puntero NULL y tomar la acción adecuada como se muestra a continuación:

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

los malloc()función de C, todavía existe en C ++, pero se recomienda evitar el uso de la función malloc (). La principal ventaja de new sobre malloc () es que new no solo asigna memoria, sino que construye objetos, que es el propósito principal de C ++.

En cualquier momento, cuando sienta que una variable que se ha asignado dinámicamente ya no es necesaria, puede liberar la memoria que ocupa en la tienda gratuita con el operador 'eliminar' de la siguiente manera:

delete pvalue;        // Release memory pointed to by pvalue

Pongamos los conceptos anteriores y formemos el siguiente ejemplo para mostrar cómo funcionan 'nuevo' y 'eliminar':

#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;
}

Si compilamos y ejecutamos el código anterior, esto produciría el siguiente resultado:

Value of pvalue : 29495

Asignación de memoria dinámica para matrices

Considere que desea asignar memoria para una matriz de caracteres, es decir, una cadena de 20 caracteres. Usando la misma sintaxis que hemos usado anteriormente, podemos asignar memoria dinámicamente como se muestra a continuación.

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

Para eliminar la matriz que acabamos de crear, la declaración se vería así:

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

Siguiendo la sintaxis genérica similar del operador nuevo, puede asignar una matriz multidimensional de la siguiente manera:

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

Sin embargo, la sintaxis para liberar la memoria para la matriz multidimensional seguirá siendo la misma que la anterior:

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

Asignación de memoria dinámica para objetos

Los objetos no son diferentes de los tipos de datos simples. Por ejemplo, considere el siguiente código donde vamos a utilizar una matriz de objetos para aclarar el concepto:

#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;
}

Si tuviera que asignar una matriz de cuatro objetos Box, el constructor Simple se llamaría cuatro veces y, de manera similar, al eliminar estos objetos, el destructor también se llamará el mismo número de veces.

Si compilamos y ejecutamos el código anterior, esto produciría el siguiente resultado:

Constructor called!
Constructor called!
Constructor called!
Constructor called!
Destructor called!
Destructor called!
Destructor called!
Destructor called!