Dynamiczna alokacja pamięci
Operator sizeof
Za pomocą operatora sizeof
możemy
poznać rozmiar zmiennej lub typu,
wyrażony w bajtach.
int a = 5, tab[] = {1, 2, 3, 4}; printf("Rozmiar typu `int` to %d.\n", sizeof(int)); printf("Rozmiar adresu zmiennej `a` to %d.\n", sizeof &a); printf( "Tablica `tab` ma %d elementów.\n", (sizeof tab)/(sizeof tab[0]) );
W przykładzie powyżej pokazano, jak sprawdzić rozmiar statycznej lub automatycznej tablicy wyrażony w liczbie elementów.
Funkcje malloc
, calloc
, realloc
oraz free
Wszystkie poniższe funkcje są zadeklarowane w pliku nagłówkowym stdlib.h
.
Aby dynamicznie zaalokować pamięć,
stosujemy funkcję malloc
,
która przyjmuje jako argument
rozmiar pamięci, jaka ma być zaalokowana.
int *p; p = malloc(sizeof *p); scanf("%d", p); printf("%d\n", *p); int *t, i; t = malloc(10 * sizeof *t); // teraz w t zapisany jest adres dynamicznie // zaalokowanej tablicy int o rozmiarze 10 elementów for(i = 0; i < 10; ++i){ scanf("%d", t+i); }
Jeśli chcemy dynamicznie zaalokować tablicę,
której elementy będą od początku wyzerowane,
możemy użyć funkcji calloc
.
long long int *tab; tab = calloc(10, sizeof *tab); assert(tab[0] == 0);
Aby zmienić rozmiar dynamicznej alokacji pamięci,
używamy funkcji realloc
.
tab = realloc(tab, 20 * (sizeof *tab));
Gdy pamięć zaalokowana dynamicznie przestaje
być potrzebna, warto ją zwolnić za pomocą funkcji free
, aby nie powstawały tzw. wycieki pamięci.
Ma to duże znaczenie szczególnie w przypadku
programów działających długo (np. z pętlą zdarzeń).
free(tab); tab = NULL;
Aby zaznaczyć, że wskaźnik tab
w przykładzie powyżej nie zawiera już żadnego poprawnego adresu,
nadajemy mu wartość NULL
.
Zadania
-
Napisz bezparametrową funkcję, która rezerwuje pamięć na pojedynczą zmienną typu
double
i zwraca adres zarezerwowanego obszaru pamięci. -
Napisz funkcję, która przyjmuje jako parametr adres wskaźnika na
double
. Funkcja zwalnia obszar pamięci wskazywany przez wskaźnik, którego adres dostała, a następnie ustawia wartość tego wskaźnika naNULL
. W programie testującym sprawdź poprawność funkcji przyrównując wartość wskaźnika doNULL
. -
Napisz program, który wczyta od użytkownika liczbę całkowitą
n
, dynamicznie zaalokuje tablicęn
liczb zmiennoprzecinkowych, wczyta je wszystkie od użytkownika, wypisze ich maksimum, minimum, średnią i sumę, a następnie zwolni pamięć zajmowaną przez tę tablicę.