3

EDIT What i am trying to achieve with the code, is to create an array of 20 unique 'Person' objects. I know now thanks to the guys below that i am going way off calling dealloc.

for (int i = 0; i < 20; i++)
{
    Person *myPerson = [[Person alloc] init];
    myPerson.name = @"Brian";
    myPerson.age = [NSNumber numberWithInteger:23];     
    [myArray addObject:myPerson];       
    [myPerson dealloc];         
}

In the process of learning Objective C, hence why this code might seem crazy to you. But I am coming from Java so my logic isn't great for Objective C yet.

I was trying to populate my array with 20 person objects. But it seems i am adding the same Object person all the time. Then deallocating it which defeats the point.

So my question is: What would be the correct way to to fill the array with 20 different person objects. The names and ages will be different in the future for each person but at the moment they all be the same while i learn.

Is the only way to do this to type a lot of code like this :

    Person *myPerson1 = [[Person alloc] init];
    myPerson.name = @"Brian";
    myPerson.age = [NSNumber numberWithInteger:23];     
    [myArray addObject:myPerson1];  
    Person *myPerson2 = [[Person alloc] init];
    myPerson.name = @"Brian";
    myPerson.age = [NSNumber numberWithInteger:23];     
    [myArray addObject:myPerson2];  
    Person *myPerson3 = [[Person alloc] init];
    myPerson.name = @"Brian";
    myPerson.age = [NSNumber numberWithInteger:23];     
    [myArray addObject:myPerson3];  

20 times? Or is there a more elegant solution?

Thanks for you advice. -Code

4 Answers 4

9

Your for loop code is correct with the exception of deallocating myPerson at the end of the loop. You do not want to deallocate it since the object is retained by the array. Generally you do not want to invoke dealloc directly, you want to use retain/release instead. For more information about memory management check out Apple's Guide

So you are correct with the exception of dealloc being changed to release.

for (int i = 0; i < 20; i++)
{
    Person *myPerson = [[Person alloc] init];
    myPerson.name = @"Brian";
    myPerson.age = [NSNumber numberWithInteger:23];     
    [myArray addObject:myPerson];       
    [myPerson release];         
}
Sign up to request clarification or add additional context in comments.

12 Comments

Stronger: The only time any normal Objective-C program will call dealloc is at the end of a class's override of dealloc, in which case you'll write [super dealloc]. Any other use is almost certainly wrong.
But is it not true to say that I have an array holding 20 copies of the same object(20 pointers to the same object)? What i am trying to do(and not understanding how) is add 20 unique objects.
@Code: No, you do not have 20 pointers to the same object. A new object is created every time you write [[Person alloc] init], which you do each iteration of the loop. It might have looked like that's what was happening with the broken code, because each time you dealloced the object, its memory location was freed and the next object was allocated at the same address.
@Code: As you see from the answer from DHamrick here, and from Rob's answer, you either have to autorelease myPerson or release myPerson. Calling dealloc is just plain wrong. The two correct techniques are both fine, but for your understanding of Objective-C (especially for iPhone, where Garbage-Collection is not supported) it is very important that you understand the two techniques.
@Code: Yep, you should. Basically you have to think of pointers in terms of owernship. Your main object owns the array, and your array owns each Person therein. Unlike in the real world, however, ownership is not exclusive -- another object could also own your array, without "diluting" your ownership of it. You signal the "taking" and "relinquishing" of such ownership with the retain and release methods. When your object dies (i.e. in dealloc), you must make sure it relinquishes all ownerships it may hold.
|
8

Probably the simplest and most "obj-c" way to do this would be to create a class method on person that creates the person you want. Just like [NSString stringWithFormat], you'd return an autoreleased object so that the caller doesn't even need to release it.

Never call dealloc yourself - trust in release

- (Person*) personWithName:(NSString*)name andAge:(NSNumber*)age
{
     Person* p = [[Person alloc] init];
     p.name = name;
     p.age = age;
     [p autoRelease];
     return p;
}

Now you'll be able to add each person to the array in a single line without leaking memory

[myArray addObject:[Person personWithName:@"Brian" andAge:23]];
[myArray addObject:[Person personWithName:@"Alice" andAge:4]];
[myArray addObject:[Person personWithName:@"Bob" andAge:60]];  

Further reading: http://www.cocoadev.com/index.pl?AutoRelease

Comments

1

As DHamrick writes you should not dealloc the object you create, this is the same as deleting the object. It was added to the array, which also retained it. But as you in the loop creates a new object I can imagine the new object will have the same address as the previously deleted one and thus the old pointers will again point at this new object, making you believe they are all one and the same. To hunt down bugs like this I suggest you look into enabling NSZombie's.

http://iosdevelopertips.com/debugging/tracking-down-exc_bad_access-errors-with-nszombieenabled.html

Comments

-1

Here is the way to create a array of object The object is get value from dictionary in which i have stored objects and key and value as a object of EmpDesignation class ..

NSMutableDictionary *Dictperson = [[NSMutableDictionary alloc]init];

[Dictperson setObject:FirstEmployee forKey:[NSNumber numberWithInt:1]];
[Dictperson setObject:SecondEmployee forKey:[NSNumber numberWithInt:2]];
NSNumber *count = [[NSNumber alloc]initWithInt:1];
//   NSInteger temp = ;
int cnt=Dictperson.count;
EmpDesignation *obj[cnt];`

3 Comments

What programming language is this ? Please provide an understandable explanation and a precise question. As of now we can not help with this question in its current state.
this is objective c sorry for complications
No need to say sorry, afterall you are trying to help people here. But I think you should format your code better.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.