0Pricing
C Academy · Lekcja

Alokowanie tablicy

Zarezerwuje Pan/Pani pamięć sterty.

Alokowanie tablicy to bezpłatna lekcja C Academy na CoddyKit. To lekcja 1 z 4. Możesz przeczytać całą lekcję poniżej za darmo — a potem ćwiczyć ją interaktywnie w przeglądarce z wbudowanym edytorem kodu i tutorem AI dostępnym 24/7. To część ścieżki edukacyjnej C Academy, a Twój postęp synchronizuje się między webem a aplikacją CoddyKit. Kurs C Academy zawiera 4 lekcji w sumie.

Dlaczego tablice dynamiczne?

Zwykła tablica ma stały rozmiar określony podczas kompilacji. Często jednak liczba potrzebnych elementów jest znana dopiero podczas działania programu.

Tablice dynamiczne rozwiązują ten problem: za pomocą malloc można poprosić system operacyjny o blok pamięci w czasie działania programu, a jego rozmiar określić zmienną.

Poznajemy malloc

malloc (memory allocate) znajduje się w <stdlib.h>. Przekazuje się mu liczbę bajtów, a on zwraca wskaźnik do tego bloku lub NULL, jeśli operacja się nie powiedzie.

Pamięć pochodzi ze sterty i pozostaje zajęta do momentu jej zwolnienia.

int *p = malloc(10 * sizeof(int));

Określanie rozmiaru za pomocą sizeof

Nigdy nie należy wpisywać liczby bajtów na stałe. Należy używać sizeof, aby kod działał poprawnie na różnych platformach.

Aby przydzielić miejsce na n liczb całkowitych, należy pomnożyć n przez sizeof(int). Często stosuje się idiom n * sizeof(*p), który wykorzystuje typ samego wskaźnika.

int *p = malloc(n * sizeof(*p));

Zawsze sprawdzaj NULL

Jeśli zabraknie pamięci, malloc zwróci NULL. Wyłuskanie wskaźnika NULL spowoduje awarię programu.

Przed użyciem należy sprawdzić wynik. Ten prosty nawyk zapobiega wielu trudnym do wykrycia awariom.

int *p = malloc(n * sizeof(*p));
if (p == NULL) {
    fprintf(stderr, "out of memory\n");
    return 1;
}

Pełne przydzielenie pamięci

Oto kompletny program, który przydziela miejsce na 5 liczb całkowitych, wypełnia je i wyświetla ich wartości.

Proszę zwrócić uwagę na symetrię: malloc na początku i free na końcu.

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

int main(void) {
    int n = 5;
    int *a = malloc(n * sizeof(*a));
    if (!a) return 1;
    for (int i = 0; i < n; i++) a[i] = i * i;
    for (int i = 0; i < n; i++) printf("%d\n", a[i]);
    free(a);
    return 0;
}

malloc nie zeruje pamięci

Pamięć zwrócona przez malloc jest niezainicjalizowana: zawiera przypadkowe dane, które znajdowały się tam wcześniej.

Odczytanie jej przed zapisem prowadzi do nieprzewidywalnych wartości. Zawsze należy przypisać wartość każdemu elementowi przed jego odczytaniem.

int *a = malloc(3 * sizeof(*a));
/* a[0], a[1], a[2] hold garbage here */
a[0] = 10;

calloc zeruje pamięć za Ciebie

calloc(count, size) przydziela miejsce na count elementów o rozmiarze size bajtów i ustawia każdy bajt na zero.

Należy go używać, gdy potrzebna jest wyczyszczona, wypełniona zerami tablica. Dodatkowo chroni przed przepełnieniem podczas mnożenia.

int *a = calloc(5, sizeof(*a));
/* every element is now 0 */

calloc w działaniu

Ten program używa calloc i potwierdza, że tablica początkowo zawiera zera, zanim ją zmodyfikujemy.

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

int main(void) {
    int n = 4;
    int *a = calloc(n, sizeof(*a));
    if (!a) return 1;
    for (int i = 0; i < n; i++) printf("%d\n", a[i]);
    free(a);
    return 0;
}

Indeksowanie bloku

Wskaźnik do bloku na stercie zachowuje się tak samo jak nazwa tablicy. Za pomocą a[i] można odczytywać i zapisywać dowolny element od 0 do n-1.

Wewnętrznie a[i] jest równoważne *(a + i).

int *a = malloc(3 * sizeof(*a));
a[0] = 1;
*(a + 1) = 2;   /* same as a[1] = 2 */
a[2] = 3;

Uważaj na zakresy

Jeśli przydzielono n elementów, prawidłowe indeksy obejmują zakres od 0 do n-1. Zapis do a[n] stanowi niezdefiniowane zachowanie.

Język C nie sprawdza zakresów automatycznie, dlatego błąd off-by-one może po cichu uszkodzić pamięć.

int *a = malloc(3 * sizeof(*a));
a[2] = 99;   /* OK, last valid index */
/* a[3] = 0;  BUG: out of bounds */

Odczytywanie rozmiaru podczas działania programu

Na tym polega prawdziwa siła tego rozwiązania: rozmiar może pochodzić z danych wejściowych, pliku lub obliczeń. Ten sam kod może przydzielić miejsce na 2 albo 2 miliony elementów.

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

int main(void) {
    int n = 6;            /* could be scanf'd */
    long *a = malloc(n * sizeof(*a));
    if (!a) return 1;
    long sum = 0;
    for (int i = 0; i < n; i++) { a[i] = i + 1; sum += a[i]; }
    printf("%ld\n", sum);
    free(a);
    return 0;
}

Szybki test

Sprawdź swoją wiedzę na temat przydzielania pamięci.

Podsumowanie

Tablicę dynamiczną można utworzyć za pomocą malloc(n * sizeof(*p)) lub przydzielić dla niej wyzerowaną pamięć za pomocą calloc(n, sizeof(*p)).

Zawsze należy sprawdzać NULL, pamiętać, że malloc pozostawia przypadkowe dane, indeksować elementy od 0 do n-1 i parować każde przydzielenie pamięci z wywołaniem free. Następnie nauczą się Państwo zmieniać rozmiar bloku z zachowaniem jego danych.

Często zadawane pytania

Czy lekcja „Alokowanie tablicy” jest bezpłatna?

Tak — pełny tekst „Alokowanie tablicy” jest dostępny za darmo tutaj w sieci. Aby ćwiczyć ją interaktywnie (wbudowany edytor kodu i tutor AI dostępny 24/7) i odblokować resztę kursu C Academy, przejdź na CoddyKit PRO. Kurs C Academy zawiera 4 lekcji w sumie.

Co nauczysz się w „Alokowanie tablicy”?

Zarezerwuje Pan/Pani pamięć sterty. Ćwiczysz C Academy z praktycznym kodem, który uruchamiasz bezpośrednio w przeglądarce, a tutor AI dostępny 24/7 odpowiada na Twoje pytania podczas pracy nad lekcją.

Czy potrzebuję doświadczenia, aby zacząć C Academy?

Nie wymagamy żadnego doświadczenia. C Academy w CoddyKit jest strukturyzowany dla początkujących i zaawansowanych użytkowników, więc możesz zacząć tutaj lub od początku i uczyć się w swoim tempie. To lekcja 1 z 4.

Ile czasu zajmuje lekcja „Alokowanie tablicy”?

Większość lekcji CoddyKit trwa około 5–10 minut. Każda lekcja to mały, interaktywny krok, dzięki czemu robisz systematyczne postępy i zawsze wracasz dokładnie do tego samego miejsca — na webie i w aplikacji.

Czy mogę pisać i uruchamiać kod w tej lekcji C Academy?

Tak. Każda lekcja C Academy zawiera wbudowany edytor kodu, więc piszesz i uruchamiasz prawdziwy kod bezpośrednio w przeglądarce i od razu otrzymujesz sprzężenie zwrotne od AI — bez konfiguracji na komputerze.

Wszystkie lekcje w tym kursie

  1. Alokowanie tablicy
  2. Powiększanie za pomocą realloc
  3. Wielokrotnego użytku typ wektora
  4. Zwalnianie pamięci i unikanie wycieków
← Powrót do C Academy