En aquest tema, aprendrem sobre l'assignació dinàmica de memòria en C utilitzant les funcions malloc i free. Aquestes funcions són fonamentals per gestionar la memòria de manera eficient i flexible durant l'execució d'un programa.

Objectius

  • Entendre què és l'assignació dinàmica de memòria.
  • Aprendre a utilitzar les funcions malloc i free.
  • Evitar errors comuns relacionats amb l'assignació dinàmica de memòria.

  1. Què és l'Assignació Dinàmica de Memòria?

L'assignació dinàmica de memòria permet als programes sol·licitar memòria durant l'execució, en lloc de definir la quantitat de memòria necessària en temps de compilació. Això és útil quan la quantitat de memòria necessària no es coneix fins que el programa està en execució.

  1. La Funció malloc

La funció malloc (memory allocation) s'utilitza per assignar un bloc de memòria de la mida especificada en bytes. La seva sintaxi és:

void* malloc(size_t size);
  • size: La quantitat de memòria en bytes que es vol assignar.
  • Retorna un punter al primer byte del bloc de memòria assignat, o NULL si l'assignació falla.

Exemple Pràctic

#include <stdio.h>
#include <stdlib.h>

int main() {
    int *ptr;
    int n, i;

    // Nombre d'elements
    n = 5;
    printf("Nombre d'elements: %d\n", n);

    // Assignació de memòria per a n elements de tipus int
    ptr = (int*)malloc(n * sizeof(int));

    // Comprovació si l'assignació de memòria ha estat exitosa
    if (ptr == NULL) {
        printf("Error: No s'ha pogut assignar memòria.\n");
        exit(1);
    }

    // Inicialització i visualització dels elements
    for (i = 0; i < n; ++i) {
        ptr[i] = i + 1;
        printf("%d ", ptr[i]);
    }

    // Alliberament de la memòria
    free(ptr);

    return 0;
}

Explicació del Codi

  1. Declaració de Punter i Nombre d'Elements:

    int *ptr;
    int n, i;
    n = 5;
    
  2. Assignació de Memòria:

    ptr = (int*)malloc(n * sizeof(int));
    
    • n * sizeof(int): Calcula la quantitat de memòria necessària per a n elements de tipus int.
    • (int*): Converteix el punter retornat per malloc a un punter a int.
  3. Comprovació de l'Assignació:

    if (ptr == NULL) {
        printf("Error: No s'ha pogut assignar memòria.\n");
        exit(1);
    }
    
  4. Inicialització i Visualització:

    for (i = 0; i < n; ++i) {
        ptr[i] = i + 1;
        printf("%d ", ptr[i]);
    }
    
  5. Alliberament de la Memòria:

    free(ptr);
    

  1. La Funció free

La funció free s'utilitza per alliberar un bloc de memòria prèviament assignat amb malloc. La seva sintaxi és:

void free(void* ptr);
  • ptr: Un punter al bloc de memòria que es vol alliberar.

Exemple Pràctic

L'exemple anterior ja inclou l'ús de free per alliberar la memòria assignada.

  1. Errors Comuns i Consells

Errors Comuns

  1. No Alliberar Memòria:

    • No alliberar la memòria assignada pot causar fuites de memòria.
    // Error: No s'ha alliberat la memòria
    int *ptr = (int*)malloc(10 * sizeof(int));
    
  2. Alliberar Memòria Múltiples Vegades:

    • Alliberar la mateixa memòria més d'una vegada pot causar comportament indefinit.
    int *ptr = (int*)malloc(10 * sizeof(int));
    free(ptr);
    free(ptr); // Error: Alliberament múltiple
    
  3. Accedir a Memòria Alliberada:

    • Accedir a memòria després d'alliberar-la pot causar errors.
    int *ptr = (int*)malloc(10 * sizeof(int));
    free(ptr);
    ptr[0] = 1; // Error: Accés a memòria alliberada
    

Consells

  • Inicialitzar Punter a NULL Després d'Alliberar:

    free(ptr);
    ptr = NULL;
    
  • Comprovar Sempre el Retorn de malloc:

    if (ptr == NULL) {
        // Manejar l'error
    }
    

Exercicis Pràctics

Exercici 1

Escriu un programa que assigni memòria per a un array de 10 elements de tipus float, inicialitzi els elements amb valors de 0.0 a 9.0, i després alliberi la memòria.

Solució

#include <stdio.h>
#include <stdlib.h>

int main() {
    float *ptr;
    int i;

    // Assignació de memòria per a 10 elements de tipus float
    ptr = (float*)malloc(10 * sizeof(float));

    // Comprovació si l'assignació de memòria ha estat exitosa
    if (ptr == NULL) {
        printf("Error: No s'ha pogut assignar memòria.\n");
        exit(1);
    }

    // Inicialització i visualització dels elements
    for (i = 0; i < 10; ++i) {
        ptr[i] = (float)i;
        printf("%.1f ", ptr[i]);
    }

    // Alliberament de la memòria
    free(ptr);

    return 0;
}

Exercici 2

Escriu un programa que assigni memòria per a un array de 5 elements de tipus char, inicialitzi els elements amb les lletres 'a' a 'e', i després alliberi la memòria.

Solució

#include <stdio.h>
#include <stdlib.h>

int main() {
    char *ptr;
    int i;

    // Assignació de memòria per a 5 elements de tipus char
    ptr = (char*)malloc(5 * sizeof(char));

    // Comprovació si l'assignació de memòria ha estat exitosa
    if (ptr == NULL) {
        printf("Error: No s'ha pogut assignar memòria.\n");
        exit(1);
    }

    // Inicialització i visualització dels elements
    for (i = 0; i < 5; ++i) {
        ptr[i] = 'a' + i;
        printf("%c ", ptr[i]);
    }

    // Alliberament de la memòria
    free(ptr);

    return 0;
}

Conclusió

En aquest tema, hem après com utilitzar les funcions malloc i free per gestionar l'assignació dinàmica de memòria en C. Hem vist exemples pràctics i hem discutit errors comuns i consells per evitar-los. L'assignació dinàmica de memòria és una eina poderosa que, quan s'utilitza correctament, pot fer els nostres programes més flexibles i eficients.

Curs de Programació en C

Mòdul 1: Introducció al C

Mòdul 2: Tipus de Dades i Variables

Mòdul 3: Flux de Control

Mòdul 4: Funcions

Mòdul 5: Arrays i Strings

Mòdul 6: Punteres

Mòdul 7: Estructures i Unions

Mòdul 8: Assignació Dinàmica de Memòria

Mòdul 9: Gestió d'Arxius

Mòdul 10: Temes Avançats

Mòdul 11: Millors Pràctiques i Optimització

Mòdul 12: Projecte i Avaluació Final

© Copyright 2024. Tots els drets reservats