Динамическое управление памятью в C: malloc, calloc, realloc, free
C предоставляет функции для ручного управления памятью во время выполнения. Они объявлены в <stdlib.h>.
| Функция | Описание |
|---|---|
void *malloc(size_t size) | Выделяет size байт, память не инициализирована. |
void *calloc(size_t nmemb, size_t size) | Выделяет массив из nmemb элементов по size байт, память обнулена. |
void *realloc(void *ptr, size_t size) | Изменяет размер блока ptr до size байт. Может переместить блок. |
void free(void *ptr) | Освобождает блок, ранее выделенный malloc/calloc/realloc. |
Динамическое выделение памяти
Если размер массива известен на этапе компиляции — используйте статический массив:
char name[100];
Если размер неизвестен заранее (например, длина вводимого текста) — используйте указатель и выделяйте память динамически:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main() {
char name[100];
char *description;
strcpy(name, "Zara Ali");
description = malloc(200 * sizeof(char));
if (description == NULL) {
fprintf(stderr, "Error - unable to allocate required memory\n");
return 1;
}
strcpy(description, "Zara ali a DPS student in class 10th");
printf("Name = %s\n", name);
printf("Description: %s\n", description);
free(description); // не забываем освободить!
return 0;
}
calloc работает так же, но обнуляет память:
description = calloc(200, sizeof(char));
Изменение размера и освобождение памяти
ОС вернёт всю память при завершении программы, но хорошая практика — освобождать её явно через free() когда она больше не нужна.
Для изменения размера используйте realloc():
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main() {
char name[100];
char *description;
strcpy(name, "Zara Ali");
description = malloc(30 * sizeof(char));
if (!description) { fprintf(stderr, "malloc failed\n"); return 1; }
strcpy(description, "Zara ali a DPS student.");
// нужно больше места
description = realloc(description, 100 * sizeof(char));
if (!description) { fprintf(stderr, "realloc failed\n"); return 1; }
strcat(description, "She is in class 10th");
printf("Name = %s\n", name);
printf("Description: %s\n", description);
free(description);
return 0;
}
Результат:
Name = Zara Ali
Description: Zara ali a DPS student.She is in class 10th
Важно: realloc может вернуть другой адрес. Всегда присваивайте результат обратно в указатель (как показано). Если realloc вернёт NULL, старый блок остаётся валидным — не теряйте его!
Распространённые ошибки
- Использование памяти после
free(use-after-free). - Двойное освобождение (double free).
- Утечка памяти — забыли вызвать
free. - Запись за границы выделенного блока (buffer overflow).
- Непроверка возвращаемого значения на
NULL.
Язык C
- Понимание ROM, PROM, EPROM и EEPROM: дизайн, программирование и идентификация
- Микропроцессоры: эволюция вычислений с запрограммированной памятью
- Управление памятью в C++: экспертное использование new и delete
- Динамическое выделение памяти в C: освоение malloc, calloc, realloc и free
- JavaDoc и документационные комментарии: полное руководство
- Динамическая память в C++: стек против кучи
- Java 10: размещение кучи на NV-DIMM через -XX:AllocateHeapAt
- Справочник по управлению обслуживанием: Практическое руководство для руководителей
- События по управлению активами 2012: топ конференций, обучения и выставок
- 4 ключевых цели эффективного управления активами