Delphi-PRAXiS
Seite 1 von 5  1 23     Letzte »    

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Object-Pascal / Delphi-Language (https://www.delphipraxis.net/32-object-pascal-delphi-language/)
-   -   Delphi Methode "Free" selbst implementieren (Assembler-Problem?) (https://www.delphipraxis.net/40867-methode-free-selbst-implementieren-assembler-problem.html)

VizeTE 22. Feb 2005 11:56


Methode "Free" selbst implementieren (Assembler-Pr
 
Hallo,

Alle von TObject abgeleiteten Klassen können per Free freigegeben werden ohne das es zu einer Exception kommt falls das entprechende Objekt nicht instanziert wurde/nil ist. Ich möchte selbst ein Free implementieren ohne diese Eigenschaft zu verlieren.
Bisher habe ich folgenden Code
Delphi-Quellcode:
TMyList = class(TList)
protected
  FDoSomething : boolean;
public
  destructor Destroy; override;
  procedure Free(DoSomething : boolean); reintroduce;
end;

destructor TMyList.Destroy;
begin
  if FDoSomething then
  begin
    ...do something...
  end;
  inherited;
end;

procedure TMyList.Free(DoSomething: boolean);
asm
  TEST   EAX,EAX
  JE     @@exit
  MOV    ECX,[EAX]
  MOV    DL,1
  CALL   dword ptr [ECX].vmtDestroy
  @@exit:
end;
Den Assembler-Code habe ich mir von TObject kopiert ohne wirklich zu wissen was er macht (wobei man die ersten beiden und letzten beiden Zeile ja erahnen kann). Das funktioniert auch soweit.
Falls der Parameter "DoSomething" der Methode "Free" gesetzt (wahr) ist soll in "Destroy" entsprechend reagiert werden.
Was ich jetzt nicht weiß ist wie ich meine Objektvariable in "Free" entsprechend dem Parameter setzen kann.

Falls jemand eine Idee hat oder mir sagen kann wo ich sowas nachlesen kann oder einen einfacheren Ansatz hat würde ich mich freuen :lol:
(Die Variable vor dem Aufruf von "Free" per property zu setzen würde sicher auch gehen, daß wollte ich aber vermeiden damit der Programmieren das nicht vergessen kann)

Ciao

Dax 22. Feb 2005 12:07

Re: Methode "Free" selbst implementieren (Assemble
 
Wieso den komplizierten Assembler hernehmen? So gehts doch auch, und dein Problem löst es gleich mit :)

Delphi-Quellcode:
destructor TMyList.Destroy(DoSomething: boolean);
begin
  if Self <> nil then
  begin
    fDoSemthing := DoSomething;
    Destroy;
  end
end;

jim_raynor 22. Feb 2005 12:12

Re: Methode "Free" selbst implementieren (Assemble
 
1. Würde ich diese Funktion nicht Free nennen. Früher oder Später wird es nur Verwirrungen geben.

2. Kannst du ganz einfach mit

Delphi-Quellcode:
if Self=nil then
die Prüfung machen.

3. Entfällt 2 dann, weil du Free direkt aufrufen kannst, wenn du deiner Funktion einen anderen Namen gibts.

himitsu 22. Feb 2005 12:17

Re: Methode "Free" selbst implementieren (Assemble
 
Schau mal dort rein, da dein Free jetzt einen Parameter besitzt, wird da vom Compiler noch zusätzlicher Code eingefügt, welcher jetzt vermutlich mit deinem AssemblerCode etwas in Konflickt gerät.

Inline Assembler und automatische Optimierung?



(oder du hast einfach nur einen Fehler beim Abschreiben gemacht)

VizeTE 22. Feb 2005 12:44

Re: Methode "Free" selbst implementieren (Assemble
 
@Dax

In der Tat, einfacher geht es nicht.:wall: (Wobei ich dann die Prüfung in der Methode "Free" durchführe, aber ich denke das wolltest du auch schreiben da du innerhalb des if-Blockes ja Destroy aufrufst) Als ich rumgetestet habe und noch Pascal statt Assembler verwendete hatte ich Free wohl noch als virtual gekennzeichnet. Von daher ging das nicht (Exception beim Aufruf ohne in die Methode zu springen). Dann habe ich wohl den Assembler-Code kopiert und das virtual entfernt und die Schuld fälschlicherweise auf den Pascal-Code geschoben)

@jim_raynor

Mein Gedanke bei der Benennung der Methode war halt der, daß jeder weiß, daß er ein instantiertes Objekt wieder mit Free freigeben muß. Wenn man dieses Objekt benutzt und Free aufruft meckert dann der Compiler, daß der Parameter fehlt. So weiß derjenige dann:
1. ja, er muß Free aufrufen
2. zum Aufruf ist ein Parameter nötig (der dann natürlich nicht DoSomething heißt sondern erkennen läßt was er tut!)
Natürlich fehlt dann hier noch "inherited Free;", sodaß meine Methode jetzt so aussieht:
Delphi-Quellcode:
procedure TMyList.Free(ADoSomething: boolean);
begin
  if Self <> nil then
  begin
    FDoSomething := ADoSomething;
    inherited Free;
  end;
end;
Deshalb habe ich ja auch "Free" mit reintroduce" gekennzeichnet. Somit gibt es nur das eine "Free" und Verwirrungen sind somit minimiert. (Zumindest würde es mich mehr verwirren wenn es auf einmal 2 Free-Methoden gibt!)

Ich denke so sollte das gehen. Falls noch Einwände bestehen würde ich mich über Eure Meinung freuen.

PS: Vielen Dank für die superkurze Antwortzeit!

VizeTE 22. Feb 2005 12:51

Re: Methode "Free" selbst implementieren (Assemble
 
@himitsu

Noch ein Grund das ohne Assembler zu lösen :wink:
Wie gesagt, ich habe keine Ahnung von Assembler.

sakura 22. Feb 2005 13:04

Re: Methode "Free" selbst implementieren (Assemble
 
Benenne die Methode trotzdem nicht Free, weil Free von Delphi an den verschiedensten Stellen genutzt wird und dabei von der Festen "Methoden-Signatur" ohne Parameter ausgegangen wird. Wenn die Free jetzt Parameter gibt (warum eigentlich), dann machst Du es für andere Entwickler nur umständlicher mit Deinen Objekten zu arbeiten.

...:cat:...

Neutral General 22. Feb 2005 13:25

Re: Methode "Free" selbst implementieren (Assemble
 
Aber warum willst du eigentlich ein eigenes Free ? :gruebel:

VizeTE 22. Feb 2005 14:22

Re: Methode "Free" selbst implementieren (Assemble
 
@Neutral General

Zitat:

Aber warum willst du eigentlich ein eigenes Free ?
Weil ich einen Parameter übergeben möchte und dabei vermieden werden soll,daß es viele Free-Methoden gibt. Normalerweise sieht man je wegen einem Free nicht extra in der Dokumentation nach was das tolles macht oder nicht macht sondern schreibt es einfach hin und gut. Wenn es aber nur meine Free gibt dann sieht das halt anders aus.


@sakura

Zitat:

enenne die Methode trotzdem nicht Free, weil Free von Delphi an den verschiedensten Stellen genutzt wird und dabei von der Festen "Methoden-Signatur" ohne Parameter ausgegangen wird.
Wäre es denn ok wenn ich den Parameter einen Defaultwert geben und mein Free somit wie das ursprüngliche Free aufgerufen werden kann? Wäre zwar nicht ganz in meinem Sinne aber, in meinen Augen, ein funktionierender Kompromiß.

MaBuSE 22. Feb 2005 14:26

Re: Methode "Free" selbst implementieren (Assemble
 
Folgende "einfache" Lösung ist auch möglich.

Delphi-Quellcode:
TMyList = class(TList)
public
  DoSomething : boolean;
  destructor Destroy; override;
end;

destructor TMyList.Destroy;
begin
  if DoSomething then
  begin
    ...do something...
  end;
  inherited;
end;
Dann kannst Du einfach mit folgenden Zeilen Deinen Zweck erfüllen.
Delphi-Quellcode:
...
var
  ml : TMyList;
...
begin
  ...
  ml := TMyList.Create;
  ...
  ml.DoSomething := True;
  ...
  ml.Free;
  ml := Nil;
  ...
end;
...
Die "ml := Nil" Zeile habe ich mir angewöhnt, da ein Free prüft ob das Objekt <> nil ist und es in diesem Fall freigibt. Danach ist aber das Objekt zwar freigegeben, aber nicht nil. Der Pointer zeigt immer noch auf die Spericherstelle wo das Objekt mal war. Ein erneuter Aufruf von Free kann dann Probleme machen.


Alle Zeitangaben in WEZ +1. Es ist jetzt 23:41 Uhr.
Seite 1 von 5  1 23     Letzte »    

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