Помощник
Здравствуйте, гость ( Вход | Регистрация )
|
|
25:04:2008, 17:22
|
|
Продвинутый ![]() ![]() Группа: Программист Сообщений: 135 Регистрация: 18:12:2005 Пользователь №: 2 707 Репутация: 0
|
Код procedure perem; var i: integer; begin ShowMessage(IntToStr(i)); end; Выводит какое-то значение ! Т.е. создаётся непустая переменная. Кто знает почему, и как с эти бороться ! P.s. - обнулять по типу i := 0 тупо и неразумно; А если у меня ТИП данных, где 100 таких переменных, мне что их все по очереди обнулять ? Проверял на Delphi 7 и Delphi 2005 ! |
|
Сообщение
#1
|
|
![]() |
|
|
25:04:2008, 17:45
|
|
============== ![]() ![]() ![]() ![]() ![]() Группа: Модеры Сообщений: 1 740 Регистрация: 11:01:2007 Пользователь №: 8 750 Специализация: specialist Репутация: 27
|
|
|
Сообщение
#2
|
|
|
|
25:04:2008, 18:06
|
|
Продвинутый ![]() ![]() Группа: Программист Сообщений: 135 Регистрация: 18:12:2005 Пользователь №: 2 707 Репутация: 0
|
Цитата Какой такой тип? Вот такой ! Код Type TDataSpec = record Avtive, PageControl, Count, ... тут штук 100 подобных переменных ..., Promo, Version: integer; Client: TClientArray; end; vat Data: TSpecData; Цитата Почему? Хм, много однако.... |
|
Сообщение
#3
|
|
|
|
25:04:2008, 18:19
|
|
============== ![]() ![]() ![]() ![]() ![]() Группа: Модеры Сообщений: 1 740 Регистрация: 11:01:2007 Пользователь №: 8 750 Специализация: specialist Репутация: 27
|
И что видно если так: ShowMessage(IntToStr(Data.Active));?
|
|
Сообщение
#4
|
|
|
|
25:04:2008, 18:25
|
|
Продвинутый ![]() ![]() Группа: Программист Сообщений: 135 Регистрация: 18:12:2005 Пользователь №: 2 707 Репутация: 0
|
Цитата И что видно если так: ShowMessage(IntToStr(Data.Active));? 440006 |
|
Сообщение
#5
|
|
|
|
26:04:2008, 06:10
|
|
============== ![]() ![]() ![]() ![]() ![]() Группа: Модеры Сообщений: 1 740 Регистрация: 11:01:2007 Пользователь №: 8 750 Специализация: specialist Репутация: 27
|
Вы точно привели пример, или нет? Или вот киньте сюда тест, где такое есть, посмотрим.
|
|
Сообщение
#6
|
|
|
|
26:04:2008, 18:48
|
|
Продвинутый ![]() ![]() Группа: Программист Сообщений: 135 Регистрация: 18:12:2005 Пользователь №: 2 707 Репутация: 0
|
Нет, не точно. Я писал вот так:
Цитата Memo1.Lines.Add(IntToStr(Data.Active)); |
|
Сообщение
#7
|
|
|
|
26:04:2008, 19:58
|
|
Продвинутый ![]() ![]() Группа: Программист Сообщений: 100 Регистрация: 27:02:2004 Пользователь №: 296 Репутация: 5
|
slavon-x86
1. Сделай TDataSpec не record'ом, а классом, и в конструкторе инициализируй поля как хошь. 2. ZeroMemory(@data, sizeof(data)) |
|
Сообщение
#8
|
|
|
|
26:04:2008, 20:19
|
|
Продвинутый ![]() ![]() Группа: Программист Сообщений: 135 Регистрация: 18:12:2005 Пользователь №: 2 707 Репутация: 0
|
Первый способ меня устраивает, но я не знаю как это сделать !
Второй даёт утечку памяти в строках ! |
|
Сообщение
#9
|
|
|
|
26:04:2008, 23:46
|
|
Продвинутый ![]() ![]() Группа: Программист Сообщений: 100 Регистрация: 27:02:2004 Пользователь №: 296 Репутация: 5
|
Первый способ меня устраивает, но я не знаю как это сделать ! Кхм... Не знаешь -- читай. Матчасть правильно учить по книжкам.Второй даёт утечку памяти в строках ! А по подробнее? В каких строках, при каком использовании, можно с кодом.
|
|
Сообщение
#10
|
|
|
|
27:04:2008, 10:22
|
|
Продвинутый ![]() ![]() Группа: Программист Сообщений: 135 Регистрация: 18:12:2005 Пользователь №: 2 707 Репутация: 0
|
Цитата А по подробнее? В каких строках, при каком использовании, можно с кодом. Вот сорс ZeroMemory: Код procedure ZeroMemory(p:pointer;i:integer); xor ecx,ecx call FillChar ret В данном примере вызов процедуры FillChar проинициализирует строки пустыми значениями, такой подход был нормальным в ранних версиях Delphi и Borland Pascal, но недопустим в последних версиях, в которых тип string по умолчанию соответствует типу LongString и суть указатель. Если значения строк перед инициализацией были не пусты, то мы получим утечку памяти. |
|
Сообщение
#11
|
|
|
|
27:04:2008, 12:36
|
|
Продвинутый ![]() ![]() Группа: Программист Сообщений: 135 Регистрация: 18:12:2005 Пользователь №: 2 707 Репутация: 0
|
Хотя я провёл тестирование и незаметил утечки...
Код type
Tzzz = record s, s1, s2: string; end; var Form1: TForm1; counter: LongInt = 0; implementation uses Unit2; {$R *.dfm} procedure TestMemory; var protocol : Tzzz; begin randomize; FillChar(protocol, SizeOf(protocol), 0); protocol.s1 := IntToStr(random(999999)); protocol.s2 := IntToStr(random(999999)); if counter mod 1000 = 0 then Form1.Caption := IntToStr(counter); inc(counter); end; procedure TForm1.Button1Click(Sender: TObject); begin repeat TestMemory; until 1 = 2; end; end. |
|
Сообщение
#12
|
|
|
|
27:04:2008, 13:57
|
|
Продвинутый ![]() ![]() Группа: Программист Сообщений: 100 Регистрация: 27:02:2004 Пользователь №: 296 Репутация: 5
|
Во-первых, AnsiString создаётся пустой.
Во-вторых, если строку нужно (пере)инициализировать заново, это делается безо всяких ZeroMemory: Код s := ''; Применение ZeroMemory ещё можно придумать при работе с PChar, но AnsiString всё делает самостоятельно. slavon-x86 Утечки памяти нет только потому, что Вы сначала создаёте protocol (неинициализированный), потом его зачищаете FillChar'ом, и только потом присваиваете осмысленные значения. После чего процедура заканчивается, protocol удаляется из стека вместе со своими полями, и никакой памяти не теряется. А попробуйте в другом порядке Код protocol.s1 := IntToStr(random(999999)); protocol.s2 := IntToStr(random(999999)); FillChar(protocol, SizeOf(protocol), 0); или сделайте protocol глобальной переменной. Потом запустите Task Manager, и посмотрите на потребление памяти. P.S. Очень советую на время экспериментов repeat заменить на for с каким-нибудь скромным пределом, порядка сотни тысяч. |
|
Сообщение
#13
|
|
|
|
28:04:2008, 05:47
|
|
Новенький ![]() Группа: Программист Сообщений: 99 Регистрация: 30:07:2007 Из: Витебск Пользователь №: 12 080 Специализация: программист Репутация: 6
|
Как вариант, чтобы не инициализировать каждое поле в записи по отдельности объяви типизированную константу в духе:
Код const EmptyDataSpec: TDataSpec = (Avtive: 0; PageControl: 0; ...); И используй в духе LocalDataSpec:=EmptyDataSpec; |
|
Сообщение
#14
|
|
![]() |
|
Текстовая версия | Сейчас: 17:05:2008 - 05:30 |