Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Основная";
Текущий архив: 2003.06.12;
Скачать: [xml.tar.bz2];

Вниз

Утечка памяти   Найти похожие ветки 

 
Екатерина   (2003-05-29 12:58) [0]

После освобождения окна не освобождается вся занимаемая им память. Когда компонентов на нем не много, то ничего страшного, но если окно достаточно сложное, со множеством компонентов, включая компоненты для работы с БД, то ой....
Как-то можно "чистить" такие хвосты?
Екатерина


 
Skier   (2003-05-29 13:06) [1]

>Екатерина (29.05.03 12:58)
Проще всего это :
1) Если у компонента может быть владелец (Owner)

задавать владельца (Owner) для всех компонент
при создании. Тогда об освобожлении таких компонент вообще не
надо будет заботится, они освободяться из свойсва Components
владельца

2) Если у компонента нет владельца

Хранить ссылки на созданные компоненты в списке (см. TList и TObjectList, или их потомки) и освобождать уже оттуда(из списка)
при закрытии(уничтожении) формы.

Вкратце так...


 
Serginio   (2003-05-29 13:36) [2]

А можно небольшой вопрос. Что такое "освобождение окна"


 
Екатерина   (2003-05-29 15:34) [3]

Все компоненты создаются в design-time, т.е. после Free окна заботится как бы и не надо об их освобождении. Но даже если их создавать ручками, устанавливать владельца (окно) и ручками же освобождать исходного состояния памяти (до create окна) не добьешся. Я использую DOA и Developer Express компоненты.


 
Skier   (2003-05-29 15:37) [4]


> Но даже если их создавать ручками, устанавливать владельца
> (окно) и ручками же освобождать исходного состояния памяти
> (до create окна)

Не понял ? Что имеется в виду ?


 
Palladin   (2003-05-29 15:47) [5]

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


 
Digitman   (2003-05-29 16:14) [6]


> Екатерина


а ты уверена, что Form.Free таки вызывается ? Форму закрывает юзер щелчком на кнопке закрытия окна или ты явно где-то исполняешь Form.Free ?


 
Skier   (2003-05-29 16:21) [7]

> Екатерина
Digitman © (29.05.03 16:14) + Если у формы есть обработчик
сообщения OnClose, то, чтобы форма освобождалась, в обработчике
нужно написать Action := caFree;


 
KA_   (2003-05-29 18:02) [8]

Skier © (29.05.03 16:21)
Это не гарантирут, что память освободится, и даже, что переменная, указывающая на окно, примет значение nil.

Екатерина (29.05.03 12:58)
Delphi использует свой собственный менеджер памяти. У него есть одна особенность. После уничтожения объекта, память не возвращается в кучу (на случай, если объект будет создаваться вновь).

Екатерина (29.05.03 15:34)
Borland рекомендует использовать не Free, а Release.


 
Skier   (2003-05-29 18:06) [9]

>KA_ © (29.05.03 18:02)

> Это не гарантирут, что память освободится

Доводы !

> и даже, что переменная, указывающая на окно, примет значение
> nil.

Причём тут "даже" ?


 
KA_   (2003-05-29 18:09) [10]


> Skier © (29.05.03 18:06)
> >KA_ © (29.05.03 18:02)
>
> > Это не гарантирут, что память освободится
>
> Доводы !

Смотри мой ответ про менеджер памяти Delphi.

> > и даже, что переменная, указывающая на окно, примет значение
>
> > nil.
>
> Причём тут "даже" ?


Потому что возможны варианты.


 
Skier   (2003-05-29 18:09) [11]

>KA_ © (29.05.03 18:02)

> После уничтожения объекта, память не возвращается в кучу
> (на случай, если объект будет создаваться вновь).

Память помечается как "свободная для выделения"


 
Serginio   (2003-05-29 18:12) [12]

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


 
KA_   (2003-05-29 18:16) [13]

Skier © (29.05.03 18:09)
Под кучей, я имел в виду кучу виндового менеджера памяти, а не делфевого.


 
Skier   (2003-05-29 18:19) [14]

>Serginio (29.05.03 18:12)
Он и прав и нет одновременно... :)
Тут нужно разобраться что такое память, здесь можно выделить 2
понятия (для нашего случая) свободная память системы и свободная память (или свободная для выделения) с точки зрения менеджера памяти (т.е. память, которую считает "свободной" МП Delphi)

И (виртуальную) память системы, которую "захватил" МП, он отдаст
сам когда это будет нужно.


 
Skier   (2003-05-29 18:22) [15]

>Serginio (29.05.03 18:12)

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

Была отличная статья Mystic-a в RSDN (за 02.2002)
Поищи на сайте журнала...


 
KA_   (2003-05-29 18:24) [16]

Skier © (29.05.03 18:19)
Складывается впечатление, что он отдает ее при выгрузке приложения :)
Еслия не прав, ткните носом.


 
KA_   (2003-05-29 18:26) [17]

Статья действительно полезная!


 
Serginio   (2003-05-29 18:28) [18]

2(Skier) По моему он про МП и говорил. Кстати провел несколько экспериментов использования в Аналоге TList динамического массива и используя все методы TLIST только выделение памяти использовал SetLength вместо Realloc и оказалось, что динамический массив во много раз быстрее, а он как раз и используе МП, и отжирает память тоже будь здоров, но ведь это все ради скорости. Даже сишники завидуют.


 
Skier   (2003-05-29 18:28) [19]

>KA_ © (29.05.03 18:24)
Конечно.
Но я думаю что речь шла о "свободной" (помеченой) памяти МП Delphi. И если мы будем правильно "работать" с памятью
(создавать/освобождать) МП, то это гарантирует нам что менеджер правильно освободит занятую память системы при выгрузке приложения.


 
Serginio   (2003-05-29 18:29) [20]

Читал,очень понравилась. Но там тоже все на пальцах. По этому и говорю, что только представляю.


 
Skier   (2003-05-29 18:30) [21]

>Serginio (29.05.03 18:28)
МП выделяет память "квантами" по 4 кб (если я правильно помню...)


 
Skier   (2003-05-29 18:32) [22]

>Serginio (29.05.03 18:29)
Какие же там "пальцы" ?!
Там даже есть блок-схемы работы МП !
Ну ты загнул ! :))


 
Serginio   (2003-05-29 18:39) [23]

На сколько эти блок схемы отражают весь код МП???
Насколько я помню из этой же статьи он сразу отжирает около мегабайта(резервирует) а выделять блок для использования он действительно может и по 4кб. Всетаки надо выделяет он из зарервированной памяти.


 
Skier   (2003-05-29 18:44) [24]

>Serginio (29.05.03 18:39)

> На сколько эти блок схемы отражают весь код МП???

Дык...и код есть в GetMem.Inc
Кроме того, включаешь птицу Use Debug DCUs и пошагово анализируешь, хоть до посинения. :)


 
Serginio   (2003-05-29 18:48) [25]

Ну огромное спасибо на счет "Use Debug DCUs". Да и особо не нужно прицип ясен. А детали тоже интересно посмотреть на Паскале.
Ты бы еще в машинных кодах посоветовал посмотреть. А резервирут память он отнюдь не по 4кб.


 
Skier   (2003-05-29 18:51) [26]

>Serginio (29.05.03 18:48)
Где я писал про резервирование по 4кб ?
Пальцем, пожалуйста...


 
Serginio   (2003-05-29 18:57) [27]

При выделении памяти он не забирает ее у системы, а только при резервировании. Я говорю в этом контексте

Skier © (29.05.03 18:30)
>Serginio (29.05.03 18:28)
МП выделяет память "квантами" по 4 кб (если я правильно помню...)

полностью понять не могу.



 
Skier   (2003-05-29 19:02) [28]

>Serginio (29.05.03 18:57)
1) А я говорю про то, что МП выделяет память квантами из
уже зарезервированной памяти системы.
2) Ты пишешь "На сколько эти блок схемы отражают весь код МП???
". Я даю тебе имя файла где лежит паскалевский код МП,
а ты - "А детали тоже интересно посмотреть на Паскале."
Разве сие не странно ?


 
Serginio   (2003-05-29 19:11) [29]

Спасибо незаметил. Посмотрю с большим удвольствием. А если бы изначально написал
МП выделяет память квантами из уже зарезервированной памяти системы. Ни какой перепалки и небыло бы.


 
Skier   (2003-05-29 19:13) [30]

>Serginio (29.05.03 19:11)
Согласен, что надо было более внятно излагать.


 
Serginio   (2003-05-29 19:49) [31]

Еще раз спасибо Skiner. Как я ошибался. Вернее предполагал, что под понятием резервирет забирает память у системы, что вполне нормально если учесть, что система буде хранить данные о выделенной памяти большого блока. На самом деле

function GetSpaceAt(addr: PChar; minSize: Integer): TBlock;
// Get at least minSize bytes address space at addr.
// Return values as above.
// Failure: returns block with addr = nil.
begin
result.size := cSpaceMin;
result.addr := VirtualAlloc(addr, cSpaceMin, MEM_RESERVE, PAGE_READWRITE);
end;
Только резервирут адреса а затем уже забирает ее у системы блоками
VirtualAlloc(loAddr, hiAddr - loAddr, MEM_COMMIT, PAGE_READWRITE)
Но при этом система должна хранить информация о всех MEM_COMMIT блоках.

Еще раз спасибо.


 
Serginio   (2003-05-30 13:00) [32]

Еще раз посыплю себе голову пеплом. Нужно внимательно читать а не прочитывать как было в моем случае. Вобщем мои первоеачальные предположения были верны. Так как МП имеет три вида менеджера памяти резервируемой, выделенной и используемой. Так МП выделяет память из зарезервированной минимально по 64 кб, а из уже выделенной выделяет для использования минимум по 4 кб. Соответственно и возвратить физическую память он может только блоком не меньше чем 64 кб когда вся выделенная память быдет неиспользованной. Этим подтверждается более быстрое удаление по сравнению с HeapFree предварительно выделенной памяти HeapAlloc в 10 раз.

При использовании памяти более 4 кб. при распределении нерерывной памяти в большую сторону МП становиться менее эффективным.

На примере TList,TMemoryStream итд. которые используют распределение непрерывной памяти в МП при достижении больших обемов 6МБ начинают жутко тормозить или вылетают из-за нехватки памяти. При этом динамические массивы вполне прилично терпят такие издевательства. Одним из предположений такого поведения динамических массивов можно объяснить тем, что при достижении определенного размера динамические массивы не используют МП, а используют напрямую виндовые HeapReAlloc.

В любом случае использовать непрерывную перераспределяемую память больших размеров тоже нерекомендуется. Лучше использованть массивы выделенной памяти болших размеров (>=64кб) при этом время доступа несколько увеличиваетя но время распределения памяти реско сокращается. И не фрагментирует память.


 
Набережных С.   (2003-05-30 18:18) [33]

>Serginio (30.05.03 13:00)

В общем и целом - бред. В частностях - тоже.


 
Serginio   (2003-05-30 18:24) [34]

Например


 
Набережных С.   (2003-05-30 18:54) [35]

>Serginio (30.05.03 18:24)

Менеджер памяти находится в файле ..\Source\Rtl\Sys\getmem.inc
Дальше сам разберешься. Почему-то мне так кажется.


 
Serginio   (2003-05-30 19:00) [36]

Да нашел я его просмотрел. Ты лучше разъясни в чем бред. А все, что написал из личного опыта.


 
Anatoly Podgoretsky   (2003-05-30 19:04) [37]

Екатерина (29.05.03 15:34)
Что бы убедиться, что есть утечка поступи так, создай в цикле Create/Free скажем раз сто и посмотри, может ложная тревога.


 
Набережных С.   (2003-05-30 19:21) [38]

>Serginio (30.05.03 19:00)

Значит, все-таки плохо смотрел. Ты погоняй его под отладчиком, посмотри когда и как выделяется память. Обрати внимание на цифру 64к. А еще на методы Commit и DeCommit. И вообще на использование VirtualAlloc и LocalAlloc.

>На примере TList,TMemoryStream итд. которые используют распределение непрерывной памяти в МП при достижении больших обемов 6МБ начинают жутко тормозить или вылетают из-за нехватки памяти.

Ну при чем тут дельфийский менеджер? Да и вообще, как это можно утверждать без привязки к конкретной системе и конкретным условиям?

>при этом время доступа несколько увеличиваетя но время распределения памяти реско сокращается

Опять же, смотри выше.


 
Serginio   (2003-05-30 19:33) [39]

Ошибся cCommitAlign:= 16*1024;
>>Ну при чем тут дельфийский менеджер? Да и вообще, как это >>можно утверждать без привязки к конкретной системе и >>конкретным условиям?
При том, что все они используют SysRealloc МП. При этом динамческие массивы с применением SetLength вполне работают нормально.
Если хочешь могу дать ссылочку на мои изыскания по этому поводу.




 
panov   (2003-05-30 19:38) [40]

Утечки памяти нет.
Это уже много раз обсуждалось.

То, что показывается в "Диспетчер задач"(Task Manager), например, только лишь отображение свойств работы менеджера памяти Windows.

Мернеджер памяти Windows сам занимается возвратом виртуальной памяти в кучу. Алгоритм работы Microsoft не раскрывает.



Страницы: 1 2 вся ветка

Форум: "Основная";
Текущий архив: 2003.06.12;
Скачать: [xml.tar.bz2];

Наверх





Память: 0.55 MB
Время: 0.009 c
14-35066
MorisTheCat
2003-05-27 22:21
2003.06.12
Поразачетов и сессий!


14-35054
Пацифист
2003-05-27 21:50
2003.06.12
Ну пожалуйста! Горю!!!!!!!!


3-34759
dimonf
2003-05-24 16:35
2003.06.12
Помогите разобраться с REPLACE в MSSQL.


3-34694
off
2003-05-15 07:19
2003.06.12
Суммирование по БД.


14-35022
sasha
2003-05-27 12:40
2003.06.12
интернет





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский