SevenDays
SevenDays

Reputation: 3768

ARC and "copy" method

I'm using SBJson to parse JSON strings.

Like this:

NSDictionary *dict = received_notification.object;

Should I use

NSString *name  = [[dict valueForKey:@"name"] copy];

or

NSString *name  = [dict valueForKey:@"name"];

I think that first method copies NSString and after that dict can be released.

But for the second expression "name" keeps a reference to dict and it can't be released.

Am I wrong?

Upvotes: 0

Views: 167

Answers (1)

LombaX
LombaX

Reputation: 17364

You are right in the first case, and copying can be useful because NSString has a mutable subclass (NSMutableString), so copy ensures that you have a real NSString in *name and not it's mutable subclass.
(More: Talking about NSString, copy is used mainly on properties, but depending on how is structured your code can be useful even on a local variable)

But in the second case you are wrong. First thing: you are using ARC (not mentioned in the post but I see the tag), so all local variables are __strong by default

When you do:

NSString *name = [dict objectForKey:@"name"]; // use objectForKey since valueForKey is for KVC, as suggested by Martin R

You are not taking a reference to the dictionary, but you are taking a reference to the object at the key "name" inside the dictionary (that should be an NSString). So, ARC sends a retain message automatically to the NSString. At that moment, that string is referenced strongly at least by two things:
- your *name pointer
- the NSDictionary

if your dictionary is deallocated, the NSString instance has another reference (from *name) and is not released until this last reference is removed.

Last thing: since in your example there are only local variables, all strong references created here are lost after the method ends (since the local variables are destroyed). The referenced objects are deallocated if they have no other strong references in other parts of the code.

Upvotes: 7

Related Questions