2012-09-26 1 views
47

Vielleicht ist dies eine schlechte Übung, aber von den Dokumentationen, die ich gelesen habe, bekam ich den Rat, Objekte in einigen Fällen innerhalb der ViewDidLoad-Methode und Null in ViewDidUnload zu initialisieren.iOS6 viewDidUnload Veraltet

Zum Beispiel, wenn Sie etwas haben, wie ein Beobachter des Hinzufügen

[[NSNotificationCenter defaultCenter] addObserver:self 
              selector:@selector(filterready:) 
               name:@"filterReady" 
               object:nil]; 

Jetzt habe ich keine Methode, um die Beobachter zu entfernen, aber die viewDidLoad genannt wird jedesmal, wenn die Ansicht dargestellt, die mehrere in mit Ergebnissen Beobachter laufen nach einer Weile und der Selektor wird dann mehrmals aufgerufen.

Ich kann das beheben, indem ich einige Reiniger in die Methode viewDidDisappear verschiebe, aber jetzt habe ich einige Zweifel, ob ich das Richtige tue.

In meinem Beispiel habe ich mehr Navigation-Controller, die ihre Subnavigationen steuern, aber die dealloc wird nie für sie genannt, obwohl sie nicht

Antwort

89

sollten Sie verwenden die - (void)didReceiveMemoryWarning und - (void)dealloc Methoden.

In iOS 6 sind die Methoden viewWillUnload und viewDidUnload von UIViewController veraltet. Wenn Sie diese Methoden zum Freigeben von Daten verwenden, verwenden Sie stattdessen die Methode didReceiveMemoryWarning. Sie können diese Methode auch verwenden, um Verweise auf die View-Controller-Ansicht freizugeben, wenn sie nicht verwendet werden. Sie müssen testen, dass die Ansicht nicht in einem Fenster ist, bevor Sie das tun.

Sie sollten also überprüfen, ob Ihre Ansicht im Fenster zuerst, dann Ihren Beobachter in der Antwort didReceiveMemoryWarning

+0

Es ist wahrscheinlich die richtige Antwort. Trotzdem ist es seltsam, dass sie diese Nachricht entfernt haben. Ich habe gelernt, das SDK zu verwenden, indem ich den Folien von Paul Hegarty folgte, und natürlich sind sie immer noch für iOS5. Ich werde dieses Jahr nach seinen aktualisierten Dias suchen, vielleicht gibt er einen guten Hinweis darauf. – Hons

+2

@Hons ist es überhaupt nicht seltsam - 'viewDidUnload' wurde, explizit nach der Dokumentation, nur aufgerufen, wenn Ihre Ansicht aufgrund einer Speicherwarnung gelöscht wird. Wenn Sie einen Beobachter in 'viewDidLoad' hinzufügen und ihn nur in' viewDidUnload' entfernen, werden Sie die Zuweisung häufig aufheben, ohne sie zu entfernen. Das lässt einen baumelnden Zeiger im Benachrichtigungszentrum zurück, der später zu einem Absturz führt. – Tommy

+0

Wie überprüfen Sie, ob sich Ihre Ansicht im Fenster befindet? – zakdances

4

Warum nicht einfach den Beobachter entfernen in der DEALLOC Funktion referenziert werden? Und wenn Sie ARC verwenden, rufen Sie nicht [Super Dealloc]

Wenn Sie Controller Dealloc-Funktion aufrufen wird nicht aufgerufen, dann müssen Sie herausfinden, warum dies ist. Vielleicht haben Sie einen NSTimer, der auf dem ViewController läuft, und wenn Sie die Ansicht öffnen, würde dies dazu führen, dass die Dealloc nicht aufgerufen wird. Oder die Ansicht wird wo anders gespeichert.

+0

der ganze Sinn der ViewDidUnload ist, dass Sie die Ansicht entladen kann und Sachen freigeben Speicher zu speichern, während die View-Controller existiert noch – user102008

+0

In iOS 6, die viewWillUnload und ViewDidUnload Methoden der UIViewController jetzt veraltet sind .... –

+0

So shouldn Sie verwende die Dealloc-Methode nicht. Weil das Objekt noch nicht zerstört werden kann. – Craimasjien

9

Alex entfernen ist gut. Aber ich mag richtige Paarung. Aus diesem Grund, es sei denn die Ansicht benachrichtigt werden müssen, wenn es nicht einmal gesehen hat, füge ich in der Regel Benachrichtigung bei viewWillAppear und viewDidDisappear

+0

viewDidUnload wird aufgerufen, wenn die Ansicht entladen wird, und viewDidDis wird nur angezeigt, wenn die Ansicht nicht mehr angezeigt wird. Benachrichtigungen, die nach der ViewDidUnload-Methode nicht registriert werden mussten, müssen ab iOS 6.0 nun mit didReceiveMemoryWarning oder dealloc aufgehoben werden –

12

Zunächst einmal, auch wenn viewDidUnload nicht veraltet, können Sie diese Meldung in viewDidUnload abzumelden gehabt haben muss UND dealloc. Schon vor iOS 6 wird viewDidUnload in den meisten Fällen NICHT aufgerufen; nur in Situationen mit wenig Speicher. Wenn Sie es also zuvor nur in viewDidUnload und nicht in dealloc eingegeben hätten, wäre die Registrierung nicht aufgehoben worden, und es wäre wahrscheinlich abgestürzt, als es freigegeben wurde und eine Benachrichtigung erhalten hat. Also musst du es vorher in dealloc setzen, damit es richtig funktioniert hat.

Zweitens, wenn Sie es vorher richtig gemacht haben, müssen Sie nichts extra dafür tun, damit es in iOS 6 korrekt funktioniert. Der einzige Unterschied in iOS 6 ist, dass Ansichten überhaupt nicht mehr entladen werden Speichersituationen). Es ist also dasselbe wie in iOS 5, wenn Sie nicht in eine Situation mit wenig Speicher geraten sind. Da Ansichten nicht entladen werden, wird viewDidLoad nur einmal aufgerufen, sodass Ihre Benachrichtigung nur einmal registriert wird.Es wird nicht registriert in dealloc, wie Sie es richtig ausgedrückt haben müssen.