C рекомендации, стек против выделения кучи


В последнее время я использую c гораздо чаще и обнаружил, что мне действительно не нравится иметь дело с управлением памятью или, по крайней мере, идея о том, что если я malloc указатель, я должен освободить его, даже если это самая тривиальная вещь. Это привело меня к выделению как можно большего количества стека и использованию & для получения его местоположения. Даже создание отдельных переменных int и inptr(у меня была некоторая проблема lvalue с оператором & в макросах).

Я не нашел много мест, где мне приходилось иметь дело с прохождением данные вверх (выше/ниже), где они были выделены. В то же время мне нужно приличное количество ранних возвратов(и я бы предпочел избегать goto). Что говорит общее мнение С. Есть ли какие-то очевидные признаки, которые я должен использовать в том или ином конкретном случае.

P.S. одна вещь, которая заставила меня немного волноваться, заключалась в том, что я недавно получил проблему повреждения памяти из-за использования неправильного sizeof для malloc, и я не заметил этого сразу, так как большинство моих путей кода непосредственно после этого момента не использовали куча. Насколько большой проблемой, по-вашему, может быть скрытие такого рода коррупции?

4 3

4 ответа:

Вы должны использовать malloc, если:

  1. Вы передаете указатели на не-static const данные в стек вызовов, или
  2. вы выделяете переменные или просто большие объемы данных (иначе вы рискуете переполнить стек).

В других случаях распределение стека должно быть в порядке.

Немного языка щека: самый верный признак, когда вы бежите из стека.

Еще одна ситуация, помимо упомянутой лармансом, когда вы хотите вернуть данные для вызывающего объекта в большинстве случаев, когда возвращаемые данные являются сложными, более эффективным является возврат указателя, чем возврат копии.

Хотя технически это не имеет прямого отношения к вопросу ОП, он находится в той же самой бейсбольной площадке (что, как я полагаю, является достаточным обоснованием для моего ответа).

Возможно, вы захотите взглянуть на " Boehm C Garbage Collector". Это проверенная временем часть программного обеспечения, и я использовал ее много раз без каких-либо проблем. Это позволяет эффективно использовать malloc для всего и просто забыть о соответствующем free.

Выделение стека полезно, когда вы имеете дело с небольшим количеством данных, и эти данные нужны только в одной функции. Если вместо этого вы должны передавать указатели между функциями, то вам лучше malloc () память в куче из-за того, что после выхода из функции ее стек может быть перезаписан каждый раз. Наличие более 127 байт локальных данных замедлит выполнение, так как если смещение находится в пределах этого предела, оно может быть включено в саму инструкцию (например, mov eax, [ebp - 4]), поэтому буферы символов должны быть размещены в куче (если вы не уверены, что они не превысят это ограничение). Еще одна вещь о free () (по цене downvoted ;): освобождение вашей памяти не требуется, если на самом деле ОС будет требовать обратно всю память, которую она дала вам приложение, но это плохая практика программирования, признак лени и может привести к утечкам памяти или любым ошибкам.