В чем разница между new / delete и malloc / free?

В чем разница между new / delete и malloc / free?

Связанные (повторяющиеся?): В каких случаях использовать malloc vs new?

Смотрите также мой подробный ответ здесь.

Jonathan H 24.12.2014 15:19
Стоит ли изучать PHP в 2026-2027 годах?
Стоит ли изучать PHP в 2026-2027 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
286
1
197 287
15
Перейти к ответу Данный вопрос помечен как решенный

Ответы 15

Наиболее существенное отличие состоит в том, что оператор new выделяет память, затем вызывает конструктор, а delete вызывает деструктор, а затем освобождает память.

Строго говоря, оператор new просто выделяет память. Это новое выражение, которое вызывает оператор new, а затем запускает конструктор в выделенной памяти.

Don Wakefield 28.10.2008 02:36

Еще одно отличие заключается в том, где распределяется память. Я недавно где-то видел, что malloc / free работают с кучей, а new / delete работают в другой области памяти, имя которой сейчас ускользает от меня. (Однако достаточно сказать, что эту другую область, вероятно, можно рассматривать как еще одну кучу.)

RobH 30.04.2009 23:29

RobH - вся память размещена в куче. Локальные переменные находятся в стеке. 'new' и malloc обычно являются одной и той же функцией, за исключением последующего вызова ctors.

Martin Beckett 06.10.2009 23:37

@mgb: Да, вы правы, объекты размещаются либо в «куче приложения», либо в стеке. Но @RobH относится к тому, что стандарт называет разными частями «кучи приложения». Есть «Куча», из которой malloc выделяет память, и «Free Store», из которой new выделяет память. Хотя в реализациях немного эти области действительно перекрываются (это деталь реализации).

Martin York 28.11.2009 05:01

Ваше утверждение на 100% верно, но просто не отвечает на заданный вопрос, см. Ответ ниже, есть причина, по которой оно больше голосов, чем ваше.

Murali 20.01.2010 19:58

Вот расширенная версия моего ответа, чтобы вы могли понять: «Наиболее существенное различие заключается в том, что оператор new выделяет память, затем вызывает конструктор, а удаление вызывает деструктор, а затем освобождает память, [в отличие от malloc / free, которые не вызывают ctors / dtors] "Я бы сказал, что один отрицательный голос (ваш), 30 положительных и 2 исправления по-прежнему считается хорошим ответом, а это означает, что большинство людей его понимают. И да, причина в том, что ответ Мартина лучше моего (он имеет 14 изменений) Кстати, я также поддержал его.

Trap 21.01.2010 04:23

Все, что я пытался сказать, это должно быть хотя бы некоторое упоминание о malloc / free, чтобы его можно было квалифицировать как сравнение, которого не хватало в вашем ответе. Тем не менее, это актуальное и точное заявление, так что положительные голоса, надеюсь, вы понимаете мою точку зрения. В любом случае, если бы только ТАК позволил мне вернуть свой голос против, я бы искренне это сделал.

Murali 22.01.2010 06:06

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

Martin York 26.01.2010 22:57

@Trap ваш ответ не отвечает на вопрос, "расширенная" версия действительно расширена (и это отвечает на вопрос), однако мне очень нравится комментарий Дона Уэйкфилда

4pie0 01.09.2013 05:21

@DonWakefield: Различие между необработанным выделением и созданием объекта действительно существует, однако ваша терминология неверна. Когда вы сказали «новый оператор», вы имели в виду «(глобальную или членскую) функцию с именем operator new()». Везде, где появляется «новый оператор», это новое выражение и вызывает конструктор, нет значимого различия между двумя терминами, которые вы использовали в своем комментарии.

Ben Voigt 16.09.2017 00:20

new вызывает ctor объекта, delete вызывает dtor.

malloc и free просто выделяют и освобождают необработанную память.

Что вы имеете в виду под сырой памятью?

Destructor 05.01.2015 18:50

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

James Curran 06.01.2015 02:04

В C++ new / delete соответственно вызывают конструктор / деструктор.

malloc / free просто выделяют память из кучи. new / delete также выделяют память.

new / delete - это C++, malloc / free - это старый добрый C.

В C++ new вызывает конструктор объектов, а delete вызывает деструктор.

malloc и free, пришедшие из темных веков до OO, только выделяют и освобождают память, не выполняя никакого кода объекта.

«Исходя из темных веков до OO» звучит так, как будто вы подразумеваете, что new / delete - это лучше, чем malloc / free, когда на самом деле ни лучше, ни хуже, просто они имеют другое применение. Обратите внимание, что я не тот, кто проголосовал против вас, я просто предполагаю.

Graeme Perrow 27.10.2008 18:19

new и delete - это C++ примитивы, которые объявляют новый экземпляр класса или удаляют его (таким образом вызывая деструктор класса для этого экземпляра).

malloc и free - это C функции, и они выделяют и освобождают блоки памяти (по размеру).

Оба используют кучу для выделения памяти. malloc и free, тем не менее, являются более "низкоуровневыми", поскольку они просто резервируют часть пространства памяти, которая, вероятно, будет связана с указателем. Никаких структур вокруг этой памяти не создается (если вы не считаете массив C структурой).

new в C++ не объявляет экземпляр класса. Он (обычно) выделяет один из кучи и ничего не объявляет. Вы можете объявить экземпляр, просто объявив его, и в этом случае он будет в стеке или в глобальных объектах, в зависимости от продолжительности хранения объявления.

Steve Jessop 27.10.2008 18:14

Что ж, он выделяет пространство памяти для класса, но вы не можете «объявить» класс в стеке, не в реальном смысле сохранения класса в стеке. Объявление включает только указатель на класс, который всегда выделяется в стеке, а фактическая память, содержащая класс, находится в куче.

Jorge Córdoba 27.10.2008 18:28

Да, ты можешь. Согласно тегам вопросов, это C++, поэтому объекты могут попадать в стек. И новое - это не декларация, а выражение. Объявление чего-либо и распределение - это разные вещи.

Steve Jessop 27.10.2008 18:40

Единственное сходство заключается в том, что оба malloc / new возвращают указатель, который адресует некоторую память в куче, и они оба гарантируют, что, как только такой блок памяти был возвращен, он не будет возвращен снова, если вы сначала не освободите / не удалите его. То есть они оба «выделяют» память.

Однако new / delete дополнительно выполняют произвольную другую работу, используя конструкторы, деструкторы и перегрузку операторов. malloc / free всегда выделяют и освобождают только память.

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

Ответ принят как подходящий

new / delete

  • Выделить / освободить память
    1. Память выделена из «Бесплатного хранилища».
    2. Возвращает полностью типизированный указатель.
    3. new (стандартная версия) никогда не возвращает NULL (выдает ошибку при ошибке).
    4. Вызываются с Type-ID (размер вычисляет компилятор).
    5. Имеет версию для явной обработки массивов.
    6. Перераспределение (чтобы получить больше места) не выполняется интуитивно (из-за конструктора копирования).
    7. Называют ли они malloc / free, определяется реализацией.
    8. Можно добавить новый распределитель памяти для работы с нехваткой памяти (std::set_new_handler).
    9. operator new / operator delete можно переопределить на законных основаниях.
    10. Конструктор / деструктор, используемый для инициализации / уничтожения объекта.

malloc / free

  • Выделить / освободить память
    1. Память выделена из «Кучи».
    2. Возвращает void*.
    3. В случае ошибки возвращает NULL.
    4. Необходимо указать требуемый размер в байтах.
    5. Выделение массива требует ручного расчета пространства.
    6. Простое перераспределение большей части памяти (конструктор копирования не о чем беспокоиться).
    7. Они будут НЕТ вызывать new / delete.
    8. Невозможно вставить пользовательский код в последовательность распределения, чтобы помочь с нехваткой памяти.
    9. malloc / free может быть переопределен НЕТ юридически.

Таблица сравнения характеристик:

Характерная чертаnew / deletemalloc / free
Память выделена из'Бесплатный магазин''Куча'
ВозвратПолностью типизированный указательvoid*
При неудачеБроски (никогда не возвращает NULL)Возвращает NULL
Требуемый размерРассчитывается компиляторомДолжен быть указан в байтах
Обработка массивовИмеет явную версиюТребуются ручные расчеты
ПерераспределениеНе обрабатывается интуитивноПростой (без конструктора копирования)
Зов обратногоРеализация определенаНет
Случаи с низкой памятьюМожно добавить новый распределитель памятиНе обрабатывается кодом пользователя
ПереопределяемыйдаНет
Использование конструктора / деструкторадаНет

Технически память, выделенная new, поступает из «свободного хранилища», а память, выделенная malloc, поступает из «кучи». Являются ли эти две области одинаковыми - это деталь реализации, что является еще одной причиной того, что malloc и new нельзя смешивать.

Может ли кто-нибудь отредактировать, чтобы уточнить, что касается «бесплатного магазина», а не кучи? Куча процесса - это хорошо известная концепция уровня операционной системы, не зависящая от языка (?); откуда взялся "Free Store"?

einpoklum 21.02.2016 18:26

@einpoklum: Это просто названия областей памяти. Ни то, ни другое не имеет ничего общего с концепцией языка, известной как «куча», или концепцией os «куча процессов». C++ намеренно определен как независимый от платформы / ОС / компилятора. Таким образом, использование конкретной концепции ОС, такой как «куча процессов», подорвет гибкость стандарта.

Martin York 21.02.2016 20:06

Для удаления проверка на нуль не требуется. OTOH, free ожидает ненулевой указатель.

winterlight 19.06.2016 14:25

@winterlight: Раньше это было правдой, но теперь нет. См .: linux.die.net/man/3/freeIf ptr is NULL, no operation is performed.

Martin York 19.06.2016 20:12

@LokiAstari Похоже, что «куча», «свободное хранилище» и «динамическая память / хранилище» являются синонимами: в Знакомство с C++ Бьярна Страуструпа он говорит: «Оператор new выделяет память из бесплатный магазин (также известного как динамическая память и куча). Стандарт C++ 14, раздел 3.7.4, посвященный Динамическое хранилище, говорит: «Объекты могут создаваться динамически во время выполнения программы (1.9) с использованием новых выражений (5.3.4) и уничтожаться с помощью выражений удаления».

Max Heiber 07.01.2017 18:07

@mheiber: в стандарте явно указано, что это могут быть отдельные области. n4567 20.7.13 C-Library параграф 5 (о malloc): It also allows malloc() to be implemented with a separate allocation arena,

Martin York 08.01.2017 22:55

@LokiAstari интересно, но я не уверен, что «разрешено находиться на отдельной арене распределения» подразумевает, что «бесплатное хранилище» - это другое понятие, чем «куча». Но тогда я не совсем понимаю, что означает «арена раздельного распределения». Вероятно, это специфично для семантики undeclare_unreachable, о которой идет речь в этом абзаце.

Max Heiber 09.01.2017 18:46

@mheiber: Значит, они могут быть одинаковыми. И несколько реализаций реализуют new путем вызова malloc (обратите внимание, что обратный способ явно не разрешен). Но в некоторых реализациях эти области памяти полностью разделены. Причина, по которой они были разделены, заключается в том, что это позволяет оптимизировать код управления памятью C++ иначе, чем управление памятью C. Дело в том, что они могут быть одинаковыми, но вы не можете предполагать, что это так.

Martin York 09.01.2017 20:43

@mheiber: Вы должны помнить, что new / delete являются неотъемлемой частью языка C++ и размещаются и выпускаются из 12.5 «Free Store». В то время как malloc и family предоставляются в виде библиотеки с совершенно другого языка, который ничего не знает о C++. В стандарте C malloc / free получает память из «Кучи». Теперь C++ внутренне разрешено использовать malloc под капотом, и в этом нет никаких требований.

Martin York 09.01.2017 20:56

@mheiber: Также "Обзор C++" предназначен для новичков, поэтому упрощение понимания вещей важнее фактических деталей реализации. Особенно, когда это мало что меняет на уровне приложений. Все, что вам нужно помнить, это то, что указатель, выделенный с помощью new, должен быть освобожден с помощью delete (не освобождается), а указатель, выделенный с помощью malloc, должен быть освобожден с помощью free (а не удаления).

Martin York 09.01.2017 20:58

Разница между «Free Store» и «Heap», продвигаемая этим ответом, не поддерживается стандартом, поскольку ни стандарты C, ни C++ не упоминают слово «куча» в этом контексте. (C вообще не упоминает об этом, а C++ говорит о кучах только в смысле структура данных.)

user4815162342 25.02.2017 14:05

@ user4815162342: Термин «Free Store» определен стандартом C++. Термин «куча» (всегда в кавычках) используется здесь просто для того, чтобы различить две области распределения (без необходимости писать книгу о различиях).

Martin York 26.02.2017 01:01

Ответ цитирует как кучу, так и бесплатное хранилище. Почему бы просто не указать, что они разные, не вводя конкретный термин для одного из них? В конце концов, «куча» обычно используется для любой области динамической памяти, включая память, выделенную new. (И он также используется C++ для обозначения структуры данных, что может только усугубить путаницу.)

user4815162342 26.02.2017 04:08

@ user4815162342: Который вы бы нашли, если бы прочитали только первые комментарии два.

Martin York 26.02.2017 05:20

Под «почему бы не уточнить» я имел в виду текст ответа. (Следует признать, что слово «указать» было легко неправильно понять в данном контексте.) Ваш комментарий касался формулировки стандарта.

user4815162342 26.02.2017 10:44

Не уверен, что это важно для кого-то, но вы можете заставить ключевое слово 'new' возвращать нулевой указатель, а не 'bad_alloc', используя (notthrow) во время создания экземпляра указателя: foo = new (nothrow) int [5];

Rob 07.03.2019 21:17

также,

глобальные new и delete можно переопределить, malloc / free не могут.

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

new делает несколько вещей, но не malloc:

  1. new создает объект, вызывая конструктор этого объекта.
  2. new не требует приведения типа выделенной памяти.
  3. Для этого не требуется выделять объем памяти, а требуется несколько объекты для строительства.

Итак, если вы используете malloc, вам нужно делать указанные выше вещи явно, что не всегда практично. Кроме того, new может быть перегружен, а malloc - нет.

Одним словом, если вы используете C++, постарайтесь максимально использовать new.

Основное различие между new и malloc заключается в том, что new вызывает конструктор объекта, а соответствующий вызов delete вызывает деструктор объекта.

Есть и другие отличия:

  • new является типобезопасным, malloc возвращает объекты типа void*.

  • new выдает исключение при ошибке, malloc возвращает NULL и устанавливает errno

  • new - это оператор, который может быть перегружен, malloc - это функция и не может быть перегружен

  • new[], который выделяет массивы, более интуитивно понятен и типобезопасен, чем malloc

  • Распределения, производные от malloc, могут быть изменены с помощью realloc, выделения, производные от new, не могут быть изменены

  • malloc может выделить N-байтовый фрагмент памяти, new необходимо попросить выделить массив, скажем, типа char

Глядя на различия, можно сказать, что malloc - это C-esque, new - C++ - esque. Используйте тот, который кажется наиболее подходящим для вашей кодовой базы.

Хотя допустимо, чтобы new и malloc были реализованы с использованием разных алгоритмов распределения памяти, в большинстве систем new внутренне реализуется с использованием malloc, что не приводит к разнице на системном уровне.

  • Чтобы использовать malloc(), нам нужно включают<stdlib.h> или <alloc.h> в программе, которая не требуется для new.
  • new и delete могут быть перегружены, а malloc - нет.
  • Используя размещение new, мы можем передать адрес, по которому мы хотим выделить память, но это невозможно в случае malloc.
alloc.h не является стандартным заголовком. <new> требуется для использования нового размещения.
M.M 03.09.2015 08:07

new и delete - операторы в C++; который тоже может быть перегружен. malloc и free - функции в c;

malloc возвращает null ptr в случае сбоя, в то время как new выдает исключение.

адрес, возвращаемый malloc, должен быть приведен снова по типу, поскольку он возвращает (void *) malloc (size) New возвращает набранный указатель.

  • new - это оператор, а malloc () - функция.
  • new возвращает точный тип данных, а malloc () возвращает void * (указатель типа void).
  • malloc (), память не инициализируется, а значение по умолчанию - мусор, тогда как в случае new память инициализируется значением по умолчанию, например, с 'ноль (0)' в случае с int.
  • delete и free () могут использоваться для указателей NULL.

1. новый синтекс проще, чем malloc ()

2. new/delete - это оператор, где malloc () / free () это функция.

3. new/delete выполняется быстрее, чем malloc () / free (), потому что новый код сборки напрямую вставляется компилятором.

4. с помощью наложения оператора можно изменить значение в программе новое / удалить.

Этот код для использования ключевого слова delete или бесплатной функции. Но при создании объект-указатель с помощью 'malloc' или 'new' и освободить память объекта с помощью удалить даже этот указатель на объект может быть функцией вызова в классе. После которые используют бесплатно вместо удаления, тогда он также работает после бесплатного оператора, но при использовании обоих, только объект-указатель не может вызывать функцию в классе .. код выглядит следующим образом:

#include<iostream>


using namespace std;

class ABC{
public: ABC(){
    cout<<"Hello"<<endl;
  }

  void disp(){
    cout<<"Hi\n";
  }

};

int main(){

ABC* b=(ABC*)malloc(sizeof(ABC));
int* q = new int[20];
ABC *a=new ABC();
b->disp();

cout<<b<<endl;
free(b);
delete b;
//a=NULL;
b->disp();
ABC();
cout<<b;
return 0;
}

output :

Hello
Hi
0x2abfef37cc20

Другие вопросы по теме