Delphi-PRAXiS
Seite 4 von 4   « Erste     234   

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Object-Pascal / Delphi-Language (https://www.delphipraxis.net/32-object-pascal-delphi-language/)
-   -   Delphi Freigeben -> AV; Bearbeiten -> Nichts weiter (https://www.delphipraxis.net/129669-freigeben-av%3B-bearbeiten-nichts-weiter.html)

jaenicke 9. Mär 2009 17:24

Re: Freigeben -> AV; Bearbeiten -> Nichts weiter
 
Naja, wenn man sich das alles richtig überlegt, dann kann man das so auch machen, man muss aber dann genau schauen welchen Speichern man reserviert und freigibt usw., da müsste man sich dann selbst drum kümmern.
Wenn man nicht ein Array in der Länge verändert, sondern direkt den Speicher manipuliert, dann berührt dies den Referenzzähler nicht. Denn die alten Referenzen werden nicht entfernt sondern nur direkt inkl. Referenzzähler an die neue Stelle kopiert. Bei den alten wird der Speicher wieder freigegeben ohne, dass die Referenzzähler dekrementiert werden.

Auf diese Weise sollte das klappen, ist aber noch mehr Handarbeit und man muss noch mehr aufpassen was man eigentlich tut.

Blup 11. Mär 2009 09:48

Re: Freigeben -> AV; Bearbeiten -> Nichts weiter
 
Das könnte so aussehen:

Delphi-Quellcode:
procedure MoveElements(var Source, Dest; ASize: DWord);
var
  BufferSize: DWord;
  Buffer, P1, P2: Pointer;
begin
  P1 := @Dest;
  P2 := @Source;
  if DWord(@Source) < DWord(@Dest) then
  begin
    BufferSize := DWord(@Dest) - DWord(@Source);
    if BufferSize > ASize then
      BufferSize := ASize
    else
      Inc(DWord(P1), ASize - BufferSize);
  end
  else if DWord(@Source) > DWord(@Dest) then
  begin
    BufferSize := DWord(@Source) - DWord(@Dest);
    if BufferSize > ASize then
      BufferSize := ASize
    else
      Inc(DWord(P2), ASize - BufferSize);
  end
  else
    Exit;

  GetMem(Buffer, BufferSize);
  Move(P1^, Buffer^, BufferSize);
  Move(Source, Dest, ASize);
  Move(Buffer^, P2^, BufferSize);
  FreeMem(Buffer);
end;

procedure TMainList.MoveContent(const AFrom, ATo, ASize: Integer);
begin
  MoveElements(FValues[AFrom], FValues[ATo], ASize);
end;
Die Grenzen des Arrays dürfen durch ASize natürlich nicht überschritten werden.
Deshalb würde ich MoveContent so ändern, dass ACount übergeben wird.

Delphi-Quellcode:
procedure TMainList.MoveContent(const AFrom, ATo, ACount: DWord);
begin
{$ifdef DEBUG}
  if (AFrom + ACount > Length(FValues)) or
     (ATo  + ACount > Length(FValues)) then
    raise Exception.Create('MoveContent -> Index überschreitet das Maximum');
{$endif}
  MoveElements(FValues[AFrom], FValues[ATo], ACount * SizeOf(FValues[0]));
end;

xZise 26. Mär 2009 18:00

Re: Freigeben -> AV; Bearbeiten -> Nichts weiter
 
Hi Blup,

Entschuldige das ich erst jetzt antworte, aber kann es sein, das du ASize als "Length" interpretiert hast?

MfG
xZise

Blup 27. Mär 2009 07:19

Re: Freigeben -> AV; Bearbeiten -> Nichts weiter
 
ASize wird in MoveElements als (Anzahl der zu verschiebenden Elemente) * SizeOf(Element) angenommen.

Ich habe aber vorgeschlagen MoveContent so zu verändern, dass nur die Anzahl der Elemente übergeben wird.
Das ist für die Verwendung einfacher und an einer zentralen Stelle kann so leicht die Überprüfung auf fehlerhafte Parametern erfolgen.


Alle Zeitangaben in WEZ +1. Es ist jetzt 00:14 Uhr.
Seite 4 von 4   « Erste     234   

Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz