0

I wonder, from a memory point of view, if what I'm doing is correct. First, the files that I want to re-use are subclasses of UIViews. In my UIViewcontroller, I declare an object like this :

World_1_ViewController.h :

#import "Level1.h"

@class Level1;

@interface World_1_ViewController : UIViewController <UIAccelerometerDelegate>
{
    Some things....
    Level1 * level1view;
}

World_1_ViewController.m :

- (void)viewDidLoad
{
    [super viewDidLoad];
    // Do any additional setup after loading the view.

    level1view = [[Level1 alloc] init];
    [self.view addSubview:level1view];

    //Other things...
}

You could see that it's init a first time when the UIViewController World_1_ViewController is opening, in the viewDidLoad method.

Now i need to re-use this object, level1view, so in one of my methods which come after, I use:

[level1view release];
level1view = [[Level1 alloc] init];
[self.view addSubview:level1view];
//Some methods...

Is it correct from a memory point of view? Or what should I do ?

javanna
  • 59,145
  • 14
  • 144
  • 125
user2057209
  • 345
  • 1
  • 6
  • 19

4 Answers4

1
[level1view release];
level1view = [[Level1 alloc] init];
[self.view addSubview:level1view];
Some methods...

in that code you should also remove your current view from superView, like that

[level1view removeFromSuperview];
[level1view release];
level1view = [[Level1 alloc] init];
[self.view addSubview:level1view];
Some methods...

also you should release level1view in dealloc and didReciveMemoryWarning methods, and set it to nil

updated:

- (void)dealloc
{
   [level1view release];
   [super dealloc];
}

- (void)didReciveMemoryWarning
{
    [super didReciveMemoryWarning];
    if (!self.isViewLoaded) {
        [level1view release];
         level1view = nil;
    }
}
BergP
  • 3,453
  • 4
  • 33
  • 58
  • I put [level1view release]; in the dealloc method of my World_1_ViewController, but what would i add in the didReciveMemoryWarning method (and even in general ?) ? What would i set to nil ? – user2057209 Mar 22 '13 at 09:32
  • So i should put all my objects like this : [level1view release]; level1view = nil; after if (!self.isViewLoaded) ? – user2057209 Mar 22 '13 at 09:34
  • not all objects, only some views, read that http://stackoverflow.com/questions/2430728/how-to-implement-didreceivememorywarning and that http://stackoverflow.com/questions/921360/iphone-memory-management-didreceivememorywarning – BergP Mar 22 '13 at 09:38
  • Looks not working when i add [level1view removeFromSuperview]; :( – user2057209 Mar 22 '13 at 10:16
  • Do you release level1view in viewdidLoad? – BergP Mar 22 '13 at 15:15
  • Nop, think i found another solution =) – user2057209 Mar 23 '13 at 15:56
0

If you have no parameter changes and just want to have same view more then once then just alloc only once like shown below

- (void)viewDidLoad
{
    [super viewDidLoad];
    // Do any additional setup after loading the view.

    if(level1view==nil)
         level1view = [[Level1 alloc] init];
    [self.view addSubview:level1view];

    Other things...
}
βhargavḯ
  • 9,786
  • 1
  • 37
  • 59
  • So you're agree with the other answer ? =) – user2057209 Mar 22 '13 at 09:33
  • Do you want to have level1view exactly once (mean one level1view in xib) or multiple instance of level1view(more than one view in xib) ? – βhargavḯ Mar 22 '13 at 09:39
  • I don't use xib, but one level1view, and re-use it after but when the first is not use for sure – user2057209 Mar 22 '13 at 09:46
  • I guess you don't need to release and alloc again as once you allocated you can reuse that object. But [self.view addSubview:level1view]; will keep adding instance of level1view so make sure to use [level1view removeFromSuperview]; in this case. – βhargavḯ Mar 22 '13 at 10:05
  • @Bhargavi A view can have only one superview, so calling addSubview with it multiple times will not add multiple instances to the view. – James P Mar 22 '13 at 10:53
  • @James a view can have only one superview but superview can have multiple view. :).Using [self.view addSubview:level1view]; at random places in your code more than once means level1view will get added in self.view that many times. Its so simple and logical. – βhargavḯ Mar 22 '13 at 10:58
  • @Bhargavi No it won't, try it. A view can have multiple subviews, but those subviews have to be different instances. – James P Mar 22 '13 at 11:26
0

use singleton method for creating instance for handling memory use like this

   static Level1 *_sharedMySingleton;

  @implementation Level1

  +(Level1 *) getLevel1Instance
    {
        @synchronized([Level1 class])
        {
            if (!_sharedMySingleton)
            {
                _sharedMySingleton = [[self alloc] init];

            }
            return _sharedMySingleton;
        }
        return nil;
    }
@end

While creating instance replace this

level1view = [[Level1 alloc] init];
[self.view addSubview:level1view];

with

 level1view = [level1view removeFromSuperview];
level1view = [Level1 getLevel1Instance];
[self.view addSubview:level1view];

Try like this.

Ganapathy
  • 4,594
  • 5
  • 23
  • 41
-2

I think you need to declare about property like this.

@interface World_1_ViewController : UIViewController <UIAccelerometerDelegate>
{
    Some things....
    Level1 * level1view;
}

@property (nonatomic,strong) Level1 * level1view;

and also use "self." or "_" to access variable via setter or getter.

If you wanna check that object is released or not, you can check "retainCount" to use "- (NSUInteger)retainCount" like this.

printf("%d\n", [_level1view retainCount]);

When retainCount is 0, that object must be released.

Takuya Takahashi
  • 453
  • 1
  • 4
  • 16
  • You shouldn't use retainCount: http://developer.apple.com/library/ios/#documentation/Cocoa/Reference/Foundation/Protocols/NSObject_Protocol/Reference/NSObject.html#//apple_ref/occ/intfm/NSObject/retainCount – James P Mar 22 '13 at 09:47
  • `retainCount` can never return 0. – bbum Mar 22 '13 at 13:27