2

我有一個主要UIViewcontroller(vcMain)與兩個UIViewControllers從主分類。子類UIViewcontrollers(vcSub1/vcSub2)只顯示一個圖像和一些更多的控件。 vcSub1和vcSub2顯示在UITabBarController中。 我已經實現didReceiveMemoryWarning這樣的:內存警告釋放了viewcontroller?

vcMain:

- (void)didReceiveMemoryWarning { 
    [super didReceiveMemoryWarning]; 

    if ([self isViewLoaded] == NO) { 
     // release the model, will be recreated in viewDidLoad 
     [_brain release], self.brain = nil; 
    } 
} 

vcSub1:

- (void)didReceiveMemoryWarning { 
    [super didReceiveMemoryWarning];  

    if ([self isViewLoaded] == NO) { 
     // will be recreated in viewDidLoad, only exists in vcSub1 
     [self.zoomBrain release], [self setZoomBrain:nil]; 

     _button = nil; // autoreleased, created programmatically 
    } 
} 

vcSub2:

- (void)didReceiveMemoryWarning { 
    [super didReceiveMemoryWarning]; 

    if ([self isViewLoaded] == NO) { 
     // nothing in here (yet) 
    } 
} 

當我第一次模擬內存警告時,似乎一切正常。

Received simulated memory warning. 
-[AppDelegate applicationDidReceiveMemoryWarning:] [Line 81] 
-[vcSub2 didReceiveMemoryWarning] [Line 102] 
-[vcMain didReceiveMemoryWarning] [Line 73] 
-[vcSub2 viewDidUnload] [Line 112] 
-[vcMain viewDidUnload] [Line 65] 
-[vcSub1 didReceiveMemoryWarning] [Line 150] 
-[vcMain didReceiveMemoryWarning] [Line 73] 
-[vcSub1 viewDidUnload] [Line 143] 
-[vcMain viewDidUnload] [Line 65] 

我可以一次又一次地做到這一點沒有問題。然而,如果我切換標籤(並因此重新加載視圖)和模擬內存再次警告我得到這個:

Received simulated memory warning. 
-[AppDelegate applicationDidReceiveMemoryWarning:] [Line 81] 
-[vcSub2 didReceiveMemoryWarning] [Line 102] 
-[vcMain didReceiveMemoryWarning] [Line 73] 
-[vcSub1 didReceiveMemoryWarning] [Line 150] 
-[vcMain didReceiveMemoryWarning] [Line 73] 
-[vcSub1 viewDidUnload] [Line 143] 
-[vcMain viewDidUnload] [Line 65] 
*** -[vcSub1 isViewLoaded]: message sent to deallocated instance 0x614de80 

info malloc-history 0x614de80表明實例是vcSub1視圖 - 控制。

Alloc: Block address: 0x0614de80 length: 192 
Stack - pthread: 0xa0425540 number of frames: 21 
    0: 0x93f7f0a3 in malloc_zone_calloc 
    1: 0x93f7effa in calloc 
    2: 0x154a2d4 in class_createInstance 
    3: 0x13165d8 in +[NSObject(NSObject) allocWithZone:] 
    4: 0x13163da in +[NSObject(NSObject) alloc] 
    5: 0x2bf0 in -[AppDelegate application:didFinishLaunchingWithOptions:] at AppDelegate.m:47 
    6: 0x8dec89 in -[UIApplication _callInitializationDelegatesForURL:payload:suspended:] 
    7: 0x8e0d88 in -[UIApplication _runWithURL:payload:launchOrientation:statusBarStyle:statusBarHidden:] 
    8: 0x8eb617 in -[UIApplication handleEvent:withNewEvent:] 
    9: 0x8e3abf in -[UIApplication sendEvent:] 
    10: 0x8e8f2e in _UIApplicationHandleEvent 
    11: 0x30b9992 in PurpleEventCallback 
    12: 0x13d3944 in __CFRUNLOOP_IS_CALLING_OUT_TO_A_SOURCE1_PERFORM_FUNCTION__ 
    13: 0x1333cf7 in __CFRunLoopDoSource1 
    14: 0x1330f83 in __CFRunLoopRun 
    15: 0x1330840 in CFRunLoopRunSpecific 
    16: 0x1330761 in CFRunLoopRunInMode 
    17: 0x8e07d2 in -[UIApplication _run] 
    18: 0x8ecc93 in UIApplicationMain 
    19: 0x28f9 in main at main.m:14 
    20: 0x2875 in start 

爲什麼如何是我vcSub1視圖 - 控制釋放?

回答

1

我想你會釋放你的對象太多次。假設你的財產是(保留),那麼你在這裏有一個bug:

[self.zoomBrain release] 
[self setZoomBrain:nil]; 

第一行將釋放zoomBrain。

第二行將釋放zoomBrain然後將其設置爲零。

你正在釋放它兩次 - 你只需要第二行。如果你使用setter方法(即setZoomBrain :),那麼它會自動釋放你以前的zoomBrain。

這同樣適用於這樣的:

[_brain release]; 
self.brain = nil; 

的調用self.brain是寫[self setBrain:nil];不同的方式 - 再次釋放將被調用兩次。

您只需要在第二條線在每種情況下:

self.brain = nil; 
+0

謝謝!在閱讀你的答案之後,我做了更多的研究,現在我得到了這個圖片;) – Kingster 2011-05-08 07:53:24