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

Вниз

Вопрос по памяти при работе с дтнамическими массивами   Найти похожие ветки 

 
den777   (2004-02-02 18:41) [0]

Вопрос по выделению и освобождению памяти при работе с динамическими массивами.

Trec = record
s:string;
i:integer;
ar:array of string;
ar1:array of TStrInt;
end;

var
ar:array of Trec;
s:string;

procedure procedure1;
var
i,j:integer;
begin
setlength(ar,0);
s:="012345678901234567890123456789012345678901234567890";
for i:=0 to ar1 do
begin
setlength(ar,length(ar)+1);
ar[i].s:=s;
end;
end;

procedure procedure2;
var
i,j:integer;
begin
setlength(ar,0);
for i:=0 to ar1 do
begin
setlength(ar,length(ar)+1);
ar[i].s:="012345678901234567890123456789012345678901234567890";
end;
end;

procedure procedure3;
var
i,j:integer;
begin
setlength(ar,0);
s:="012345678901234567890123456789012345678901234567890";
for i:=0 to ar1 do
begin
setlength(ar,length(ar)+1);
ar[i].s:="012345678901234567890123456789012345678901234567890";
setlength(ar[i].ar,10);
for j:=low(ar[i].ar) to high(ar[i].ar) do
begin
ar[i].ar[j]:=s;
end;
setlength(ar[i].ar1,10);
for j:=low(ar[i].ar1) to high(ar[i].ar1) do
begin
ar[i].ar1[j].s:=s;
ar[i].ar1[j].i:=2;
end;
end;
end;

1.Почему при работе procedure1 выделяется оперативной памяти в несколько раз меньше
чем, при работе procedure2.
2.Как при ar1=10 000 000 и длине s в 1000 символов procedure1 нормально
отрабатывает, занимая при этом в WIN2000 не более 80 Мб оперативки,
хотя тупое умножение ar1 на длину s даст 10Гб.
3.При отработке procedure3, где заполняются вложенные динамические массивы и последующем
setlength(ar,0) вся памтять вновь освобождается. При тестировании под memprof программы
работающей по сокетам и написанной под D5, memprof постоянно указывал при подобных
операциях на неосвобожденную память.Приходилось делать что-то типа
for i:=0 to setlength(ar) do
begin
ar[i].s:="";
.... //для всех динамически распределенных переменных что-то похожее
end;
и только потом давать setlength(ar,0)
После этого memprof переставал ругаться.
Как все-таки правильно, где и какая логика во всех вышеприведенных примерах.
Если есть статья по данной теме, киньте ссылочку.


 
MBo   (2004-02-02 18:46) [1]

Собственно говоря, во всех примерах логики практически нет.
Увеличивать на каждом шаге длину массива на 1 вредно.

Обрати внимание на List-объекты (TList, TStringList)

>занимая при этом в WIN2000 не более 80 Мб оперативки,
хотя тупое умножение ar1 на длину s даст 10Гб.
физически строка - всего одна, в других элементах массива просто ссылка на нее же.


 
Тимохов   (2004-02-02 18:51) [2]

Нет времени разбираться во всем коде, но по поводу

> 1.Почему при работе procedure1 выделяется оперативной памяти
> в несколько раз меньше
> чем, при работе procedure2.


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


 
den777   (2004-02-02 19:01) [3]


> Увеличивать на каждом шаге длину массива на 1 вредно.

Знаем, проходили. Просили ответ, а не новые вопросы.

> физически строка - всего одна, в других элементах массива
> просто ссылка на нее же.

Не просто ссылка, а есть наверняка какой-то определенный механизм работы Delphi с памятью в таких случаях. Потому что при последующем ar[2].s:="fgdf" в ar[0].s,ar[1].s,ar[3].s и т.д. ничего не меняется, если была бы просто ссылка и ничего более, то изменилось бы во всех элементах сразу


> Обрати внимание на List-объекты (TList, TStringList)


Вопрос был не как лучше реализовать какую-то конкретную ситуацию, а помочь прояснить механизм работы представленных кодов, пусть и просто теоритических.


 
Тимохов   (2004-02-02 19:04) [4]


> 2.Как при ar1=10 000 000 и длине s в 1000 символов procedure1
> нормально
> отрабатывает, занимая при этом в WIN2000 не более 80 Мб
> оперативки,
> хотя тупое умножение ar1 на длину s даст 10Гб.

С этим ясно, см. мой предыдущий ответ.
Если ты потом модифицируешь каждую строку s в каждой записи(например, добавишь символ), то получишь свои 10 гб.


 
den777   (2004-02-02 19:06) [5]


> В дальнейшем, если в строке сделать изменения, то для для
> такой строки создаться особая копия, где и будут делаться
> изменения.


Что-то подобное я и представлял. Хотелось-бы прочитать какую-нибудь статью на данную тему


 
Тимохов   (2004-02-02 19:08) [6]


> Что-то подобное я и представлял. Хотелось-бы прочитать какую-нибудь
> статью на данную тему

Всем вам статью подавай!
Почитай штатный хелп.
Раздел object pascal reference\memory managment.
Там все, обсуждаемое здесь, есть.


 
Palladin   (2004-02-02 19:11) [7]


> den777 (02.02.04 19:06) [5]

Интересно и что в этой статье должно быть написано? Ваши требования к ней?


 
den777   (2004-02-02 19:12) [8]


> Раздел object pascal reference\memory managment.


Спасибо, почитаю.


 
Тимохов   (2004-02-02 19:14) [9]


> Palladin © (02.02.04 19:11) [7]

Когда-то давно была книга по дельфи 2.
Там на уровне асм. кода было расписано как работают строки.
Очень было познавательно. До сих пор многое от тудова помню.
Не знаю есть ли такие же книги по современным версиям дельфи.


 
Palladin   (2004-02-02 19:23) [10]


> Тимохов © (02.02.04 19:14) [9]

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



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

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

Наверх




Память: 0.47 MB
Время: 0.011 c
1-38876
Asd
2004-02-04 21:18
2004.02.13
Не главное окно поверх всех других приложений


1-38877
Maxim Vetera
2004-02-03 10:15
2004.02.13
Экраная лупа


14-39087
Думкин
2004-01-23 18:12
2004.02.13
С днем рождения! 23 января!


8-38972
Dmitriy O.
2003-10-14 10:29
2004.02.13
Как узнать какие цвета используются в файле BMP


14-39065
Pilum
2004-01-24 14:43
2004.02.13
Насильственная ассимиляция русских в Латвии





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
Английский Французский Немецкий Итальянский Португальский Русский Испанский