![]() |
Freigabe von Objekten (Observerpattern)
Hallo,
ich habe folgendes Problem: Infos: Ich besitze ein ObjektX mit der Vererbung class(TInterfacedObject, IInterfaceX). Dessen Referenz übergebe ich an ein normales Objekt. Dieses normale Objekt meldet nun über das Interface Veränderungen an das ObjektX. Problem: Wenn das normale Objekt(befindet sich in einem Array) mit .free /.freeandnil / .destroy freigegeben wird, wird das ObjektX scheinbar mitgelöscht, wodurch es beim Erstellen eines neuen normales Objekts zu einer Zugriffsverletzung kommt. Ich konnte bisher etwas bezüglich eines Referenzzählers herrausfinden, jedoch nicht wie die automatische Löschung umgehbar ist. Bisher bin ich deswegen gezwungen, auf .free zu verzichten. Wenn ihr hilfreiche Tipps habt lasst es mich wissen :-D |
AW: Freigabe von Objekten (Observerpattern)
Willkommen in der DP :dp:
Zitat:
Grundsätzlich kann man die automatische Freigabe eines Objektes hinter einem Interface verhindern, indem man manuell seine Methode
Delphi-Quellcode:
aufruft. Dadurch wird der Referenzzähler um 1 erhöht und somit nicht 0 (was eine Zerstörung des Objekts auslösen würde), nachdem das letzte Interface gelöscht wurde.
AddRef
Aber, meine Empfehlung: Wenn Interfaces, dann konsequent. Nicht Interfaces mit normalem Objektzugriff mischen. Das macht nur Kopfschmerzen. Also stell lieber die Stellen, wo du noch direkt auf das Objekt zugreifst, auch auf Interfaces um, dann hast du das Problem nicht und die Referenzzählung erledigt alles automatisch (nur bei zyklischen Referenzen musst du aufpassen). |
AW: Freigabe von Objekten (Observerpattern)
Zitat:
|
AW: Freigabe von Objekten (Observerpattern)
Hier mal veranschaulicht
Delphi-Quellcode:
type
IObjectX = interface end; TObjectX = class( TInterfacedObject, IObjectX ) end; procedure Test; var LObj : TObjectX; LIntf : IObjectX; begin LObj := TObjectX.Create; // RefCount ist 0 LIntf := LObj; // RefCount+1 -> 1 LIntf := nil; // RefCount-1 -> 0 -> Instanz wird freigegeben LObj.Free; // rumms, ist ja nix mehr da an der Referenz end; |
AW: Freigabe von Objekten (Observerpattern)
Danke erstmal,
der genauere Code ist in 4 Units eingeteilt. Hauptunit beinhaltet das ObjektX und das ObjektN Die Unit von ObjektN speichert die Referenz auf das ObjektX als Interface UHaupt: ObjektN: Array of TObjektN; ObjektX: TObjektX; Code der Zugriffsverletzung verursacht: ObjektN[x] := TObjektN.create(ObjektX); ObjektN[x].freeandnil; ObjektN[x] := TObjektN.create(ObjektX); <== UObjektX: TObjektX = class(TInterfacedObject, IObserverObjektX) UObjektN: TObjektN = class var ObjektX: IObserverObjektX; UObserverObjektX IObserverObjektX = Interface(IInterface) |
AW: Freigabe von Objekten (Observerpattern)
Entweder nur mit der Instanz oder nur mit dem Interfacezeiger arbeiten. *NIE* nicht niemals kombiniert. Warum, hat seine Durchlaucht Rufo schon wunderbar erklärt.
|
AW: Freigabe von Objekten (Observerpattern)
Danke für die Antworten.
Ich habe das Problem jetzt so gelöst, dass ich eine weitere Variable des Interfaces gespeichert habe, wodurch der Referenzzähler nichtmehr auf 0 geht, wenn ein Objekt gefreet wird, welches eine Interface-Referenz gespeichert hat. |
AW: Freigabe von Objekten (Observerpattern)
Man kann natürlich auch mit Intf._AddRef rumspielen, oder die Referenzzählung direkt beeinflussen.
Siehe TComponent, welches Interfaces ohne Referenzzählung implementiert, wobei die Freigabe der Instanz also standardmäßig weiterhin ausschließlich über den Owner und .Free geregelt wird, oder eventuell auch über eingebettete VCL-Interfaces, welche die Kontrolle übernehmen. Aber Grundsätzlich ist dein Vorgehen eher "falsch". Entweder du nutzt das Objekt als Objekt und verwendest keine Interfaces, oder du nutzt das Objekt ausschließlich nur noch über Interface-Referenzen und schon gibt es keine Probleme damit. |
AW: Freigabe von Objekten (Observerpattern)
![]() Ist halt nur doof, wenn man die Instanz freigibt und irgendjemand hat da noch die Finger drauf :stupid: |
Alle Zeitangaben in WEZ +1. Es ist jetzt 11:09 Uhr. |
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 by Thomas Breitkreuz