Главная страница
Top.Mail.Ru    Яндекс.Метрика
Текущий архив: 2004.03.03;
Скачать: CL | DM;

Вниз

Создание динамической струскуры хранения данных.   Найти похожие ветки 

 
Vuk ©   (2004-02-19 19:01) [40]

Для примера. Вот код, который реализует список методов с минимальным сервисом (добавление/удаление/доступ к элементам) на основе того класса, фрагменты которого я приводил. Все вполне типизировано.


type
TMethodList = class(TObject)
private
FMethods: TCLArray;
function GetMethods(index: integer): TMethod;
procedure SetMethods(Index: integer; Value: TMethod);
function GetCount: integer;
public
constructor Create;
procedure Add(Handler : TMethod);
procedure Remove(Handler : TMethod);
procedure Delete(Index: integer);
property Count: integer read GetCount;
property Methods[index:integer]: TMethod read GetMethods write SetMethods;
end;

constructor TMethodList.Create;
begin
inherited Create;
FMethods := TCLArray.Create(10, 10, sizeof(TMethod));
end;

procedure TMethodList.Add(Handler : TMethod);
begin
FMethods.Add(@Handler);
end;

function TMethodList.GetMethods(index: integer): TMethod;
begin
Result := TMethod(FMethods.Items[index]^);
end;

procedure TMethodList.Remove(Handler : TMethod);
var
i : integer;
begin
i := FMethods.IndexOf(@TMethod(Handler));
if i <> -1 then
FMethods.Delete(i);
end;

procedure TMethodList.Delete(Index: integer);
begin
FMethods.Delete(Index);
end;

procedure TMethodList.SetMethods(Index: integer; Value: TMethod);
begin
FMethods.Items[index] := @Value;
end;

function TMethodList.GetCount: integer;
begin
Result := FMethods.Count;
end;


Для примера можете подумать, что нужно для реализации того же самого на динамических массивах. Особенно это касается удаления. :o)


 
Владислав ©   (2004-02-19 19:08) [41]

> Тимохов © (19.02.04 18:58) [39]

Возможно я некорректно выразился, но именно это и имел ввиду. Утечки памяти нет. Фраза означала, что проверить, есть утечка или нет, поможет подобный код.

> Vuk © (19.02.04 19:01) [40]

Оценил бы, да понятия не имею, что такое TCLArray. Просветите плиз.


 
romeo ©   (2004-02-19 19:12) [42]


> Тимохов © (19.02.04 17:26) [11]

CopyMemory плохо только в этом случае, или лучше вообще этим не пользоваться? Например, для копирования значений из одного массива в другой, типа:

var
DinArr: array of integer;
const
Arr: array [0..50] of integer = (1, ...);

SetLength(DinArr, Length(Arr))
CopyMemory(DinArr, @Arr, Length(Arr)*SizeOf(Integer))


Или тоже лучше делать почленное копирование?


 
Владислав ©   (2004-02-19 19:15) [43]

В данном случае ничего плохого не произойдет. Правда всегда есть оговорка ;) Вот она: Если, например, к типу Integer не преобразованы указатели на переменные типа string ;)


 
Vuk ©   (2004-02-19 19:16) [44]

to Владислав:
>Просветите плиз.
Привожу только интерфейс. Полный код - это слишком много. Писалось сие давно, поэтому по интерфейсу и реализации это что-то среднее между TList и коллекциями из Turbo Pascal (касается управления памятью).

TCLArray = class( TCLContainer )
protected
FCount : integer;
FLimit : integer;
FDelta : Integer;
FItemSize : integer; { размер одного элемента }
FItems : Pointer; { указатель на непрерывный блок памяти, содержащий элементы массива }

function Get( Index : integer ) : Pointer; override;
procedure Put( Index : integer; Item : Pointer ); override;
function GetCount: integer; override;
procedure AssignTo( Dest : TPersistent); override;
procedure AppendItem( Item : pointer; AssignMode : boolean ); override;
procedure SetLimit( ALimit : integer ); virtual;
procedure CheckIndex( Index : integer );
procedure SetCount( NewCount : integer );
procedure IndexError;

public
constructor Create( ALimit, ADelta, AItemSize : Integer );
destructor Destroy; override;
procedure Add( Item : pointer ); override;
procedure Clear; override; {обнуление всех элементов}
procedure Swap( Index1, Index2 : integer ); override;
procedure Insert( Index : integer; Item : pointer );
function IndexOf(Item: pointer): integer; override;
procedure Delete( Index : integer ); override;
procedure DeleteAll; override; {удаление всех элементов}

property Items;
property Count : integer read FCount write SetCount;
property Limit : integer read FLimit write SetLimit;
property Delta : integer read FDelta write FDelta;
property ItemSize : integer read FItemSize;
property Data : pointer read FItems;
end;


 
Тимохов ©   (2004-02-19 19:18) [45]


> Владислав © (19.02.04 19:15) [43]


> Если, например, к типу Integer не преобразованы указатели
> на переменные типа string ;)

Глубоко копаете. Но в случае если это указатели, преобразованные к integer, никакого подсчета ссылок и для почленного копирование не будет.

> romeo © (19.02.04 19:12) [42]

Для массивов integer все будет ок.


 
Владислав ©   (2004-02-19 19:28) [46]

> Тимохов © (19.02.04 19:18) [45]

Смайлик, однако...

Подсчета ссылок не будет. Будет, как пить дать, обращение по битым ссылкам (это относится только к вашему утверждению. Типа, почти оффтоп).

> Vuk © (19.02.04 19:16) [44]

Ну судя по приведенному, именно не типизированное, приведенное в типизированное :) Типа, одобрям :) Надо взять на заметку.
А вот это ADelta (если я правильно понял) просто здорово. Чего, боюсь, автору вопроса очень не хватает. В общем, очень интересно!


 
Vuk ©   (2004-02-19 19:34) [47]

>А вот это ADelta (если я правильно понял) просто здорово.
Delta - это значение (в элементах массива), на которое увеличивается размер массива при вызовах Add и Insert, если количество элементов уже достигло максимально возможного на данный момент (limit). В TList происходит то же самое, но регулировать величину приращения нельзя - она вычисляется автоматически. В принципе, обе стратегии выделения памяти имеют право на существование. Если бы я писал сейчас, то у меня Delta задавалась бы в процентах от текущего размера.


 
Владислав ©   (2004-02-19 19:48) [48]

> Vuk © (19.02.04 19:34) [47]

"...задавалась бы в процентах от текущего размера."

Ну да, конечно, но зависит, таки от конкретной задачи. Я у себя отказался от ТАКОГО "расширения". Проценты "увеличивают" размер занимаемой памяти каждый раз на все большую величину. Я в своей задаче не знал, как он будет увеличиваться. Остановился на таком варианте. Сначала проценты (до некоторого размера), потом жестко заданный прирост.

Насчет дельты, надеюсь, Вы меня поняли :)


 
Vuk ©   (2004-02-19 20:10) [49]

to Владислав:
>Насчет дельты, надеюсь, Вы меня поняли
Ну... В принципе, для таких вещей можно сделать что-то типа отдельных классов, которые реализуют разные стратегии управления памятью, а класс-массив уже использует какой-то из таких классов для своей работы. Тогда можно будет реализовать сколько угодно таких стратегий и даже менять их налету. :o)



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

Текущий архив: 2004.03.03;
Скачать: CL | DM;

Наверх




Память: 0.56 MB
Время: 0.019 c
1-6025
Layner
2004-02-19 09:29
2004.03.03
Есть 2й массив, X на Y, как узнать сумму одного столбца?


1-6036
Владимир Березин
2004-02-17 18:45
2004.03.03
Мониторинг состояния Thread а


14-6255
ZeBriD
2004-02-09 19:41
2004.03.03
Подскажите, люди у кого фантазия хорошая!!!


4-6276
dit
2003-12-24 11:40
2004.03.03
процеду ра ловушки


3-5996
Bless
2004-02-04 16:33
2004.03.03
Почему хп после отката возвращает набор данных?