powered by simpleCommunicator - 2.0.61     © 2026 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / C++ [игнор отключен] [закрыт для гостей] / Про память и delete
13 сообщений из 13, страница 1 из 1
Про память и delete
    #32511507
MikeG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Привет всем!

Есть базовая структура
struct Base
{
int a;
}
и порожденная
struct Der : public Base
{
int b;
}
то есть никаких выделений памяти и виртуальных функций
Нормально ли очистится память, если выполнить следующее:

Base *b = new Der;
delete b;

и что будет, если выполнить такое:

char *c = new double;
delete c;

Спасибо
...
Рейтинг: 0 / 0
Про память и delete
    #32511611
Мышьяк
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
1) Вообще я бы не рекомендовал этого делать (особенно если собственные операторы delete и new , про стандартные не знаю)
Для этого существует виртуальный деструктор
virtual ~Base() {}

2)А это вообще не скомпилируется:
cannot convert from 'double *' to 'char *'
И поэтому такое делать нехорошо.
Хотя думаю, что стандартный delete это скушает.
...
Рейтинг: 0 / 0
Про память и delete
    #32511716
MikeG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Спасибо, Мышьяк.
Во втором примере должно быть:

char *c = (char*)new double;
delete c;

В Borland C++ 3.1 такой код не приводит к утечке памяти
(coreleft() до и после совпадают)
Причем все нормально даже при таком коде:
char *c = (char*)new double;
c=c+10; // вроде c теперь указывает вообще в другое место
delete c;

Что означает, что стандартный delete это "скушает" ? :)

Хотелось бы по подробнее узнать о том, как работает и кушает
delete и кто отвечает за пямять.
И одинаков ли принцип работы delete в компиляторах C++ под DOS
и Visual C++, Builder C++ под Windows
Может, где статейка есть, подскажите :)

Спасибо
...
Рейтинг: 0 / 0
Про память и delete
    #32512522
Фотография CEMb
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Код: plaintext
1.
2.
char *c = (char*)new double;
c=c+ 10 ; // вроде c теперь указывает вообще в другое место
delete c;
Да, всё нормально.

delete на самом деле просто освобождает область кучи для использования.
после выполнения delete память не чистится (если тока деструктор не отрабатывает) и указатель остаётся "жив". (для навернячности, люди его сразу к нулю приравнивают)
Таким образом, delete c+10 высвободит байт памяти, который находится на 10 от выдленного.

Код: plaintext
char *c = (char*)new double;
выделит кусок в четыре байта, но потом будет работать тока с первым.
гораздо веселее вариант
Код: plaintext
double *c = (double*)new char;
:)
...
Рейтинг: 0 / 0
Про память и delete
    #32512548
Фотография Палестинец
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
char *c = (char*)new double;
c=c+10; // вроде c теперь указывает вообще в другое место
delete c;
Да, всё нормально.

Ничего не нормально..
Высвобождать можно только тот указатель под который и была выделена память.
Даже не знаю на каком у вас компиляторе c=c+10 может пройти..
Имхо, ни на каком..

для выделения памяти , new и delete оперируют функциями malloc, free..
см. msdn.
...
Рейтинг: 0 / 0
Про память и delete
    #32512695
Фотография CEMb
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
авторНичего не нормально..
Нет, кое-что нормально:

Код: plaintext
1.
2.
char *c = (char*)new double;
//c=c+ 10 ; // вроде c теперь указывает вообще в другое место
delete c;

Или так:

Код: plaintext
1.
2.
char *c = (char*)new double;
c=c+ 10 ; // вроде c теперь указывает вообще в другое место
//delete c;

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

Во втором случае, тоже всё нормально. Компилятор это съест. Ибо встречая указатель на char который c+=10; компилятор не будет лазить по коду и проверять, а не сделали ли на него new double? или валидный ли это указатель кучи :) К тому же это вообще не компилятора уже дело, это можно проверить только во время выполнения.
...
Рейтинг: 0 / 0
Про память и delete
    #32512743
Фотография Палестинец
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
То что умрет нормально это так..
для обычных динамических массивов любых типов можно всегда делать
delete (char*)

Другое дело что delete можно подсунуть указатель на объект. Тут все посложней (иногда возникает желание скастовать если отнаследован от какого-то класса скажем и т.п.).. вот тут нет. какого типа создан такой и удалять..
...
Рейтинг: 0 / 0
Про память и delete
    #32513986
MikeG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Теперь вроде понятно :)
Получается так:

За выделение и освобождение памяти отвечает ОС (сис вызовы или api).
ОС каким-то образом хранит информацию о каждом выделенном блоке (начальный адрес
и размер блока). Может в каких-нить таблицах...

Так что системным функциям типа free(),VirtualFree() достаточно передать указатель на начало блока
и освободится столько памяти, сколько было выделено под этот блок.
Этот указатель может быть указателем на любой тип,
даже на структуру или класс без конструктора и деструктора.
Причем для массивов не обязательно ставить квадратные скобочки delete [] p;

Но типы нужно точно соблюдать, когда имеем дело с классами, у которых есть конструктор и деструктор, в которых также может выделяться память.
И в последнем случае очень важно ставить квадратные скобочки delete [] p;

Спасибо всем!
...
Рейтинг: 0 / 0
Про память и delete
    #32514003
MikeG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Еще забыл добавить:
если пытаться сделать delete над левым указателем (c+=10), то ОС выдаст Access Violation.
...
Рейтинг: 0 / 0
Про память и delete
    #32514129
Фотография CEMb
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
авторЗа выделение и освобождение памяти отвечает ОС (сис вызовы или api).
ОС каким-то образом хранит информацию о каждом выделенном блоке (начальный адрес
и размер блока). Может в каких-нить таблицах...

для любого массива в виндах верно следующее:

размер в байтах iS динамического массива vM:

int iS = ((long*)vM)[-4];

Кто-нить когда-нить пользовался отрицательными индексами в массивах? ;)
...
Рейтинг: 0 / 0
Про память и delete
    #32514598
vitaly_p
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
CEMbдля любого массива в виндах верно следующее:
Совсем не для любого, зависит от алгоритма работы используемого менеджера памяти.
...
Рейтинг: 0 / 0
Про память и delete
    #32515394
MikeG
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Я пробовал в консольном VC и в Builder'е:

char *c = new char[256];
int sz = ((long*)c)[-4];
ShowMessage(sz); // printf("%d",sz);
delete [] c;

Ни в одном случае не получил 256 :(
...
Рейтинг: 0 / 0
Про память и delete
    #32516702
Фотография CEMb
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Руки мыли?

используйте _msize();
...
Рейтинг: 0 / 0
13 сообщений из 13, страница 1 из 1
Форумы / C++ [игнор отключен] [закрыт для гостей] / Про память и delete
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]