Совет Майкла звучит - если вы выходите, вам не нужно беспокоиться о том, чтобы освободить память, так как система все равно ее исправит.
Единственное исключение - сегменты разделяемой памяти - по крайней мере, в общей памяти System V. Эти сегменты могут сохраняться дольше, чем программа, которая их создает.
Один из вариантов, не упомянутых до сих пор, заключается в использовании схемы распределения памяти на арене, построенной сверху стандарта malloc()
. Если все приложение использует одну арену, ваш код очистки может освободить эту арену, и все будет освобождено сразу. (APR - Apache Portable Runtime) - обеспечивает функцию пулов, которая, как мне кажется, схожа, «C-интерфейсы и реализации» Дэвида Хэнсона предоставляет систему распределения памяти на арене, я написал одну, которую вы могли бы использовать, если бы захотели.) может думать об этом как о сборе мусора бедных людей.
Как общая дисциплина памяти, каждый раз, когда вы распределяете память динамически, вы должны понимать, какой код собирается ее освободить и когда ее можно будет освободить. Существует несколько стандартных шаблонов. Самый простой - «выделяется в этой функции, освобождается до возвращения этой функции». Это позволяет хранить память в значительной степени под контролем (если вы не запускаете слишком много итераций в цикле, который содержит выделение памяти), и масштабирует его, чтобы он мог быть доступен для текущей функции и функций, которые она вызывает. Очевидно, что вы должны быть достаточно уверенны, что функции, которые вы вызываете, не собираются уклоняться (кэшировать) указатели на данные и пытаться повторно использовать их позже после того, как вы выпустили и повторно использовали память.
Следующий стандартный образец иллюстрируется fopen()
и fclose()
; есть функция, которая выделяет указатель на некоторую память, которая может быть использована вызывающим кодом, а затем освобождается, когда программа закончила с ней. Однако это часто становится очень похожим на первый случай - обычно рекомендуется называть fclose()
в функции, которая называется fopen()
.
Большинство оставшихся «узоров» - это несколько ad hoc.
Вы можете даже использовать функцию atexit() и написать функцию, чтобы освободить всю память, выделенную в связанном списке (которая в этом случае должна была быть глобальной переменной) при простом вызове exit() - таким образом, вы бы Не следует забывать не использовать простой выход(). –
Но почему? Операционная система уже поддерживает список выделенной памяти. Вы дублируете эту функциональность, просто замедляете процесс закрытия без каких-либо преимуществ, кроме как немного инфляции эго. Если вы не планируете переносить свое приложение на MSDOS, пусть os выполнит свою работу. – Eclipse
Причина в том, что в конечном итоге дисциплина и функциональность помогут вам отслеживать утечки памяти. Если вы правильно закодируете его, его можно отключить с помощью определений DEFINE или MACRO. – ojblass