Volver a la lista

Asignación dinámica de memoria: `malloc` y `free`

Se explica por qué se asigna memoria dinámicamente durante la ejecución de un programa, las diferencias entre la pila y el montón, y por qué las fugas de memoria son peligrosas.

Intermedio
|
10min
|
Verificado (2026-07)
memoria dinámicamallocfreememoria heapmemoria stackfuga de memoria
Progreso0/23 (0%)

Asignación dinámica de memoria: malloc y free

Al finalizar este tema

Comprenderá las diferencias entre la memoria de pila (stack) y la de montón (heap), por qué es necesaria la asignación dinámica y por qué se producen las fugas de memoria.


Dos tipos de memoria

La memoria utilizada por un programa se divide principalmente en dos regiones: la pila (stack) y el montón (heap).

text
Dirección alta ┌──────────────┐
          │     Stack       │ ← Asignación/liberación automática cada vez que se llama a una función
          │      ↓ hacia abajo    │
          │      ↑ hacia arriba   │
          │              │
          │              │
          │      Heap        │ ← Asignación/liberación directa por el programador
          │    Heap        │ ← Asignación/liberación directa por el programador
Dirección baja └──────────────┘
PilaMontón
AsignaciónAutomática (al llamar a la función)Manual (malloc)
LiberaciónAutomática (al finalizar la función)Manual (free)
TamañoPequeño y fijo (normalmente unos pocos MB)Grande y dinámico (hasta el límite de la RAM)
VelocidadMuy rápidaLigeramente más lenta
UsoVariables locales, argumentos de funciónDatos cuyo tamaño se desconoce

¿Por qué es necesaria la asignación dinámica?

Si creas una variable en la pila, debes conocer su tamaño en tiempo de compilación:

c
int arr[100];  // 100 elementos — determinado en tiempo de compilación

Sin embargo, si el usuario pregunta: «¿Cuántos datos va a ingresar?», no se puede saber la respuesta hasta que se ejecute el programa. En estos casos, se utiliza la asignación dinámica:

c
int n;
printf("¿Cuántos? ");
scanf("%d", &n);

int *arr = malloc(n * sizeof(int));  // Asignar n elementos durante la ejecución

malloc(asignación de memoria) asigna la cantidad de bytes solicitada desde el área de memoria dinámica (heap).


malloc y free

c
#include <stdlib.h>

// Asignación
int *data = malloc(5 * sizeof(int));

// uso
for (int i = 0; i < 5; i++) {
    data[i] = i * 10;
}

// liberación
free(data);
data = NULL;  // asignar a NULL para mayor seguridad

Si se proporciona malloc, se puede usar la memoria y, una vez que se termine de usar, se debe devolver a free. Si no se realiza free, esa memoria no se liberará hasta que finalice el programa.


Fuga de memoria

c
void process() {
    int *data = malloc(1000000 * sizeof(int));
    // procesamiento de datos...

    if (error) {
        return;  // salir sin liberar!
    }

    free(data);
}

Si esta función termina con un error, free no se ejecuta. No se liberan 1 millón de enteros (aproximadamente 4 MB). Si esta función se llama 1000 veces, se pierden 4 GB de memoria. Esto es una fuga de memoria (memory leak).

Las fugas de memoria son peligrosas porque el programa no se cierra inmediatamente. Consume memoria gradualmente hasta que todo el sistema se vuelve lento y, finalmente, falla por falta de memoria (OOM). En los programas de servidor, esto puede provocar fallos repentinos después de unos días.


Solución en lenguajes de alto nivel: recolección de basura

Python, JavaScript, Java y Go tienen un recolector de basura (GC) que se encarga de liberar la memoria automáticamente:

python
def process():
data = [0] * 1000000
# Al finalizar la función, no queda ninguna variable que referencie a data
# → GC recupera automáticamente la memoria

El programador no necesita llamar a free. El recolector de basura (GC) verifica periódicamente si “ninguna variable apunta a esta memoria” y la recupera.

El costo es:

Manual (C)Automático (Python/Java)
Posibilidad de fugas de memoriaAlta (error del programador)Baja (el GC se encarga)
RendimientoPredeciblePuede haber una breve pausa durante la ejecución del GC
Complejidad del códigoAlta (gestión de free)Baja (no requiere atención)

Rust ha elegido un tercer camino: ni GC ni free manual; el compilador rastrea el ciclo de vida de las variables e inserta automáticamente el código de liberación.


Esencial

La pila se asigna y libera automáticamente, mientras que el montón es gestionado directamente por el programador. Se asigna en el montón con malloc y se libera con free; omitirlo provoca una fuga de memoria. Los lenguajes de alto nivel resuelven este problema automáticamente mediante GC, pero comprender por qué es necesaria la gestión de memoria es fundamental en la informática.

💬 Preguntas y comentarios

0 comentarios

Puedes publicar sin iniciar sesión. Los comentarios de invitados no pueden editarse ni eliminarse después.

0/2000

Cargando...