2011-07-30 8 views
2

UIViewControllerのNSArrayを持っていて、配列にリリースを送信すると、UIViewControllersごとにviewDidUnloadまたはdeallocが呼び出されますか?どちらか?UIViewControllerのNSArrayにリリースを送信していますか?

- (void) viewDidLoad { 
    UIViewController* profileController = [[ProfileController alloc] init]; 
    .......... 
    //all the other controllers get allocated same way 

    self.viewControllers = [[NSMutableArray alloc] initWithObjects: profileController, dietController, exerciseController, progressController, friendsController, nil]; 

    [profileController release]; 
    //other controllers get released same way .... 
} 

- (void) dealloc { 
    [viewControllers release]; 
    NSLog("DEALLOC!"); 
    //I know dealloc is being called 
    //what happens to the view controllers? 
} 

が、私はこれらのビューコントローラのそれぞれについて、viewDidUnloadとのdeallocメソッドにブレークポイントを入れて、それらが呼び出されません。

は、ここで私がやっているものです。

答えて

1

上記のpgbは、メモリ管理とView Controllerのライフサイクルの2つの概念を混同しています。 viewDidUnloadは、ビューコントローラビューがアンロードされたときはいつでも呼び出されます。もちろん、ビューがロードされた場合にのみ発生します。 View Controllerのいずれかが表示されていない場合は、viewDidUnloadがまったく呼び出されるとは限りません。

deallocあなたは非常に多くのことを期待する必要があります!

あなたの問題はviewControllers配列の初期化である:viewControllersが保持属性を使用している性質であると仮定すると

self.viewControllers = [[NSMutableArray alloc] 
           initWithObjects: profileController, 
               dietController, 
               exerciseController, 
               progressController, 
               friendsController, 
               nil]; 

、これは配列、したがって、すべての配列の内容をリークします。問題は、あなたが変更可能な配列をalloc'd(したがってcount = 1を保持している)して、それを保持カウントをインクリメントするviewControllersプロパティに代入していることです。

あなたのdeallocメソッドでは、(正確に)配列を解放しますが、これは単に保持カウントを1に減らします。

私の修正案は、上記のコードにautoreleaseを追加することです:

self.viewControllers = [[[NSMutableArray alloc] 
           initWithObjects: profileController, 
               dietController, 
               exerciseController, 
               progressController, 
               friendsController, 
               nil] autorelease]; 

この変更を行った後、あなたがdeallocがビューコントローラ上で呼び出されて見ることを期待すべきです。また、これらのビューコントローラのビューがアンロードされると(たとえば、ナビゲーションコントローラベースのアプリケーションでスタックからポップされるなど)、viewDidUnloadが呼び出されると予想されるはずです。

+0

うわー。私は完全にそれを逃した...あなたは絶対に正しいです。私は通常NSMutableArray = [[NSMutableArray alloc] init ...]と[a release]のような一時変数を使用しますが、今回は簡潔にしておきました。ありがとうございました –

0

私はここで二つの問題、呼び出されていない各メソッドのいずれかを参照してください。UIViewControllerに関連付けられているviewがロードされなかった場合

viewDidUnloadは呼び出されません。基本的には、メモリー管理(およびオブジェクトのライフサイクル)とビュー・コントローラーのライフ・サイクルという2つの概念を混在させています。両者の間にいくつかの並列性が見えますが、それらは必ずしも関連しているとは限りません。

いつでもviewControllerのビューが表示されるようにしていますか?あなたがしていない場合は、viewDidUnloadは必ず呼び出されません(viewDidLoadはありません)。

deallocについては、オブジェクトを解放した後に呼び出されない場合(オブジェクトはメモリからdeallocになるはずです)、メモリリークがあるからです。あなたのコードでは、私は簡単に初期化コードでメモリリークを見ることができます:

UIViewController* profileController = [[ProfileController alloc] init]; 
.......... 
//all the other controllers get allocated same way 

self.viewControllers = [[NSMutableArray alloc] 
           initWithObjects: profileController, 
               dietController, 
               exerciseController, 
               progressController, 
               friendsController, 
               nil]; 

profileController取得その、最初の行にぶつかっretainCountときallocこと。後でNSMutableArrayに追加すると、配列はretainとなり、retainCountに再度当てられます。このバランスをとるには、releaseを2回必要としますが、deallocメソッドではreleaseを1回送信するだけです。あなたが不足している余分なreleaseを追加し、ビューコントローラのretainreleaseのコールのバランスをとるだろう

UIViewController* profileController = [[[ProfileController alloc] init] autorelease]; 
.......... 
//all the other controllers get allocated same way 

self.viewControllers = [[NSMutableArray alloc] 
           initWithObjects: profileController, 
               dietController, 
               exerciseController, 
               progressController, 
               friendsController, 
               nil]; 

:この問題を解決するために、私はあなたに、初期化を変更します。

+0

配列が割り当てられた直後にprofileControllerを解放しました。[profileController release]; –

0

配列を解放すると、配列は解放されません。これにより、他の保持がない場合に割り当てを解除することができます。

同様に、配列が解放されると、内部の各要素は解放されますが、オブジェクトは他の場所に保持される可能性があるため、すぐに解放されることは保証されません。

一般に、ビューまたはビューコントローラのようなオブジェクトは、アクティブに表示されている間はUIロジックによって保持されます。したがって、直接または配列を通じて保持を解除しても、それが解除されても(例えば、ナビゲーションコントローラのスタック内に)表示される。

関連する問題