В чем разница между инициализацией этой структуры этими стратегиями? - PullRequest
2 голосов
/ 01 июня 2010
// the malloc style, which returns a pointer:
struct Cat *newCat = malloc(sizeof(struct Cat));

// no malloc...but isn't it actually the same thing? uses memory as well, or not?
struct Cat cat = {520.0f, 680.0f, NULL};

По сути, я могу получить инициализированную структуру этими двумя способами. Мое предположение: это то же самое, но когда я использую malloc, мне также нужно освободить это Во втором случае мне не нужно думать о памяти, потому что я не называю malloc. Может быть.

Когда я должен использовать стиль malloc, а когда другой?

Ответы [ 5 ]

6 голосов
/ 01 июня 2010

Это не та же самая память, первая выделяется в куче, а вторая - в стеке.

Куча позволяет вам вручную управлять созданием и удалением со всеми плюсами и минусами: вы можете передать указатель другим, но вы также должны удалить его.

Всякий раз, когда вторая вообще возможна, она предпочтительна.

4 голосов
/ 01 июня 2010

Функция malloc должна использоваться только в том случае, если вам нужно, чтобы структура дожила до времени жизни текущей функции. Функция malloc выделяет память из кучи, что позволяет ей долго жить. Это полезно, если вам нужно хранить элементы после выхода из функции (например, в общем списке).

Также вводятся дополнительные накладные расходы, включая ...

  • Принудительная проверка ошибок в вашем коде
  • Разделение выделения и инициализация структуры
  • Затраты в процессе отслеживания памяти

С другой стороны, второй синтаксис выделяет память в стеке. Это полезно, потому что память здесь автоматическая в том смысле, что вам не нужно об этом думать. Память освобождается, так сказать, при выходе из функции. Кроме того, он допускает один оператор для выделения и инициализации.

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

3 голосов
/ 01 июня 2010

Во-первых, первый вариант не инициализирует никакой структуры. Он просто выделяет блок необработанной памяти, достаточный для хранения объекта типа struct Cat. Память остается неинициализированной (содержит мусор). Второй вариант инициализирует каждое поле в структуре определенным значением.

Во-вторых, первый вариант создает безымянный [и неинициализированный] struct Cat объект с выделенным сроком хранения. Объект будет жить до тех пор, пока вы явно не освободите его с помощью free (или пока программа не завершится). Второй вариант создает именованный объект cat с автоматическим сроком хранения - он будет автоматически освобожден в конце своей декларативной области (в конце содержащего блока).

В-третьих, на практике два варианта создают объекты в разных видах памяти. Первый вариант создает объект в куче, тогда как второй вариант обычно создает его в стеке.

Что касается того, когда использовать то или иное, здесь довольно много ответов здесь на этот вопрос. В этой теме есть несколько ответов и множество ссылок.

2 голосов
/ 01 июня 2010

Разница (среди уже упомянутых) заключается в том, что вы вообще не инициализируете структуру в первом случае (malloc); Вы просто получаете память, чтобы держать это. Во втором случае у вас есть память и инициализация.

1 голос
/ 01 июня 2010

В дополнение к другим очень полезным ответам, есть еще одно ключевое отличие.

Метод malloc () оставляет элементы структуры неинициализированными. Вы должны инициализировать их в отдельном шаге.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...