Objective-C - Testen, ob die Objektinstanz dealloced / freigegeben wird

7

Es gibt eine Möglichkeit, zu testen, ob eine objective-c-Instanz dealloced / freigegeben ist (retain count == 0) ??

Beispiel: Objekt A hat eine Referenz (Zeiger) auf Objekt B, aber Objekt B kann in niedrigen Speicherstufen freigegeben werden, wie teste ich Referenz B, um sicherzustellen, dass es freigegeben wurde?

%Vor%

Danke !!

    
jlpiedrahita 11.06.2009, 20:06
quelle

6 Antworten

11

Sie können nicht testen, ob ein Objekt deallociert wurde, da das Objekt offensichtlich nicht mehr da ist. Wenn Sie b auf Null setzen, wenn Sie es freigeben (z. B. indem Sie self.b = nil ausführen), können Sie auf nil testen und das Objekt dann erstellen.

    
Chuck 11.06.2009, 20:10
quelle
13

Wenn Sie die Umgebungsvariable NSZombieEnabled festlegen, werden dealloced Objekte zu Instanzen von NSZombie . Diese werden ausgelöst, wenn sie als nächstes gemeldet werden, was dazu führt, dass der Code abstürzt und brennt - genau das, was Sie zum Debuggen dieser Situation benötigen.

Ссылка

Aktualisieren : Für XCode 4.0 siehe Anleitungen Aktivieren Sie NSZombie in Xcode?

    
user23743 12.06.2009 01:02
quelle
3

Da die Variable b vollständig intern in der Klasse A ist und nicht als @public deklariert ist (der Standardwert ist @protected ), ist es am besten zu wissen, ob b freigegeben wurde und setzen Sie den Zeiger auf nil . Auf diese Weise können Sie if (b == nil) überprüfen und ggf. eine neue Instanz erstellen.

Die größere Frage ist jedoch, was das wahre Natur- und Speicherverhalten von b ist. Sie geben an, dass "Objekt B im Speicher in niedrigen Ebenen freigegeben werden kann", erklären aber nicht warum. Wenn Sie die Standard-Idiome für Retain-Release in Objective-C verwenden, würde ich denken, dass A derjenige wäre, der bestimmt, ob B freigegeben werden soll, da es eine neue Instanz erstellt. Wenn Sie nicht vorhaben, dass A solche Entscheidungen trifft, führt das Zulassen eines neuen B zu einer Verwirrung des Eigentums und zu Speicherproblemen auf der Straße.

Wenn A nicht für B zuständig ist und wenn Sie Leopard (oder höher) und die Garbage Collection aktiviert haben, was? Vielleicht möchten Sie eine Nullstellung als schwache Referenz . Dies wird mithilfe von __weak vor einer Instanzvariablendeklaration deklariert und verhindert nicht, dass der Garbage Collector das Objekt sammelt, auf das er zeigt. (Ein "starker" Verweis ist der Standardwert, und der Garbage Collector wird Objekte nicht freigeben, die von einem Stamm nur über starke Referenzen verfolgt werden können.) Außerdem wird der GC für Sie automatisch schwache Referenzen auf 0 setzen, wenn / wenn das Objekt vorhanden ist freigegeben.

Wenn Sie zurück zur "größeren Frage" gehen, außer b ist bereits eine schwache Referenz und GC ist eingeschaltet (und ein paar andere Bedingungen sind erfüllt), wird das System B nicht automatisch für Sie freigeben. Wenn der Grund für die Freigabe von b darin besteht, dass Instanzen von B im Laufe der Zeit anwachsen (z. B. ein Cache verzehrbarer Elemente), wäre es viel besser, eine Möglichkeit zum Leeren von B zu haben. co_de% Methode. Solch ein Ansatz würde die Verwirrung darüber, ob -removeAllObjects immer noch existiert, vermeiden und ist viel effizienter als das wiederholte (De-) Zuordnen von Objekten.

    
Quinn Taylor 11.06.2009 22:07
quelle
2

Wenn Sie b ordnungsgemäß beibehalten, wird die Zuweisung unter Bedingungen mit wenig Speicher nicht aufgehoben.

Das heißt, es sei denn, Sie heben die Zuweisung selbst auf. In diesem Fall ist es wichtig, dass Sie Referenzen darauf manuell entfernen (indem Sie sie durch nil ersetzen)

In diesem Fall genügt es, den Wert für nil zu testen:

%Vor%

Wenn Ihre Objekte automatisch freigegeben werden, müssen Sie Ihren Code überprüfen, um sicherzustellen, dass Sie ihn ausreichend gespeichert haben.

    
Alex Brown 11.06.2009 20:13
quelle
0

Sie könnten versuchen, NSLog-Nachrichten in die Objekte dealloc Methode zu schreiben. Das wird Ihnen zumindest sagen, wann das Objekt freigegeben wird.

    
Abizern 11.06.2009 20:54
quelle
-3

würde ein "try-catch" funktionieren?

%Vor%     
john ellis 17.03.2011 17:28
quelle

Tags und Links