Когда и почему использовать malloc?

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

вот мой код :

#include <stdlib.h>

int main(int argc, const char *argv[]) {

  typedef struct {
    char *name;
    char *sex;
    int age;
  } student;


  //Now I can do two things
  student p;

  //or
  student *ptr = (student *)malloc(sizeof(student));

  return 0;
}

зачем выделять память, когда я могу просто использовать student p;?

5 ответов


malloc используется для динамического выделения памяти. Как уже говорилось, это динамическое распределение, которое означает, что вы выделяете память во время выполнения. Например, когда вы не знаете объем памяти во время компиляции.

один пример должен очистить это. Говорят, Вы знаете, что будет максимум 20 студентов. Таким образом, вы можете создать массив со статическими 20 элементами. Ваш массив сможет вместить максимум 20 студентов. Но что, если вы не знаете количество студентов? Скажем, первый вход число студентов. Это может быть 10, 20, 50 или любой другой. Теперь вы введете N = количество студентов во время выполнения и выделите столько памяти динамически, используя malloc.

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

посмотрите на man page функции malloc(3).


вы используете malloc когда вам нужно выделить объекты, которые должны существовать за пределами времени выполнения текущего блока (где копирование при возврате также будет дорогостоящим), или если вам нужно выделить память больше размера этого стека (т. е.: локальный массив стека 3 мб-это плохо идея).

прежде чем C99 представил VLA's, вы также нужны it для выполнения выделения массива динамического размера, однако, он необходим для создания динамического структуры данных, такие как деревья, списки и очереди, которые используются многими системами. вероятно, есть еще много причин, это всего лишь несколько.


немного расширяя структуру примера, рассмотрим следующее:

#include <stdio.h>

int main(int argc, const char *argv[]) {

typedef struct {
 char* name;
 char* sex;
 char* insurace;
 int age;
 int yearInSchool;
 float tuitionDue;
}student;


//Now I can do two things
student p;

//or
student *p = (student *)malloc(sizeof(student));

return 0
}

C a-это язык, который неявно передается по значению, а не по ссылке. В этом примере, если мы передадим " p " функции для выполнения некоторой работы над ней, мы создадим копию всей структуры. Это использует дополнительную память (общее количество пространства, которое потребуется конкретной структуре), медленнее и потенциально не масштабируется хорошо (подробнее об этом через минуту). Однако, проходя * p, мы не проходим всю структуру. Мы только передаем адрес в памяти, который относится к этой структуре. Объем передаваемых данных меньше (размер указателя), поэтому операция выполняется быстрее.

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


malloc = выделение памяти.

Если вы прошли через другие языки программирования, вы могли бы использовать 'новые' ключевое слово.

Malloc делает то же самое в C. Он принимает параметр, какой размер памяти должен быть выделен, и он возвращает переменную указателя, которая указывает на первый блок памяти

весь блок памяти, который вы создали в памяти. Пример -

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

теперь *p укажет на первый блок последовательный 20 целочисленный блок, зарезервированный в памяти.

вы можете пройти через каждый блок с помощью оператора ++ и--. Всего хорошего.


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