2010-01-02 2 views
0

Я храню некоторые классы с параметрами WideString, описывающими их (например, имя, описание и некоторые другие). Теперь, если я изменю все эти WideStrings на простую «строку» (я использую псевдоним на самом деле, поэтому мне нужно изменить только одну строку), использование памяти примерно на 5% больше! чем ранее ... Как это возможно, так как каждый символ строки в два раза меньше WideChar?Delphi, проблема с использованием памяти с широким пространством, не-unicode VCL (D7)

благодарит заранее!

m.

+0

Как вы измеряете использование памяти? –

+0

Проводник Windows Sysinternals, также стандартный диспетчер процессов (ctrl alt del) – migajek

+0

Какой счетчик? В этом случае использование Mem в Менеджере задач бесполезно. В этом случае размер виртуальной машины лучше. –

ответ

4

Менеджер памяти Delphi не освобождает всю неиспользованную память операционной системы. Фрагментация также может сильно ударить. Оба зависят от фактического менеджера памяти, который вы используете (FastMM обычно лучше, чем менеджер запаса памяти в D7, но любой менеджер памяти может быть доведен до колен, используя определенные в памяти шаблоны использования памяти). Кроме того, WideStrings, хотя они являются COM-строками, не подсчитываются ссылкой и могут быть выпущены даже позже обычных строк.

Единственный надежный способ запроса реального сообщения памяти в Delphi - попросить менеджера памяти, который использует ваша программа Delphi. Эта функция в модуле System делает это для вас:

function GetHeapStatus: THeapStatus 

--jeroen

редактировать: 20100104 в ответ на комментарий Марко: (FastMM, как правило, лучше, чем менеджер акции памяти в D7, но любой менеджер памяти может быть поставлен на колени с использованием определенной серии папок памяти менеджера памяти)

+1

+1 фрагментация кучи или использование памяти с помощью синдрома проксикслера. FastMM лучше не работает. В частности, если код был ранее настроен, старый может быть быстрее. Таким образом, в то время как Fastmm лучше в целом, правило бенчмаркинга (измерение!) По-прежнему применяется. –

+0

Спасибо, я отредактировал ответ из-за вашего комментария. –

0

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

Для примера предположим, что у вас есть около 100 Кбайт текста при использовании строк ANSI, и вместо этого вы конвертируете его в Widestrings. Только те 100KB будут затронуты, но эти 100KB не представляют собой каждый отдельный байт памяти вашей программы. Пространство будет использоваться для форм, дескрипторов, чисел и других объектов, но поскольку они не изменяются при преобразовании, они, очевидно, не потребуют больше памяти, чем до преобразования.

+0

ОК, но разница * * * между версией unicode и non-unicode является изменением строки/ширины. *ничего больше*. Данные генерируются из одного файла и точно совпадают (как и ожидалось). Данные состоят примерно из 3/4 строк. Я проверил его на довольно большом фрагменте данных, в результате получилось дополнительно 45 Мб в памяти (43 в случае использования WideString), и он полностью воспроизводится. – migajek

0

WideStrings использует другой менеджер памяти (один из окон), а затем AnsiStrings (Delphi's) и ссылается на другие. Как вы измеряли использование памяти? С каким инструментом и с каким точным счетчиком?

0

Как вы измеряете память? Память IIRC WideString выделяется с помощью SysAllocString() и тем самым обходит диспетчер памяти Delphi.

0

Менеджер памяти в Delphi всегда занимает больше памяти, чем это действительно нужно. Это такое улучшение скорости.

0

Используете ли вы тип AnsiString или ShortString, если не используете WideString? Возможно ли, что вы компилируете с флагом компилятора {$ H-} (либо глобально, либо в какой-либо единице), который обрабатывает все типы «String» как ShortString? Если ваши строки имеют тип ShortString и вы не указываете размер строки, тогда выделенная память всегда 256 байтов.