0

When I declare a property for an interface that is Mutable should I always make it (nonatomic, copy)? Also when would I used assign instead of retain?

rolling_codes
  • 15,174
  • 22
  • 76
  • 112
  • 1
    When you're developing for iOS4 or earlier and can't use Automatic Reference Counting. Does that apply to your situation? Assign is for primitive types (BOOL, NSInteger) or object pointers you don't own. Retain is for objects w pointers in memory. Copy creates a separate copy so you can leave the original intact. If you're not working w old code, you should look into ARC and more modern examples. If you're curious, see here: http://stackoverflow.com/questions/2255861/property-and-retain-assign-copy-nonatomic-in-objective-c?rq=1 – mc01 Jun 20 '14 at 03:08

2 Answers2

1

Use nonatomic when you care more about performance than thread safety. Atomic properties are thread safe but slower. The default behaviour is atomic.

Use copy when you want a copy to be made whenever a new value is set to the property. Note that in many cases, copy will not actually make a copy of the object, so this usually has no performance impact but can solve bugs if somebody gives you a mutable copy (eg, you have an NSString property and somebody assigns an NSMutableString.

Do not ever use retain or strong as these are only needed when ARC is turned off, and you should always have ARC turned on. strong and retain are the same, and this is the default behaviour with ARC enabled. Just turn ARC on and ignore these ones, except for backwards compatible code.

Sometimes, for example delegate properties, using retain or strong would create a memory leak. In these situtaions you need to use weak or assign. In general, you should use weak, as assign can have rare edge case bugs.

Abhi Beckert
  • 32,787
  • 12
  • 83
  • 110
  • why do not use retain anymore? – rolling_codes Jun 20 '14 at 03:03
  • 1
    @Savagewood sorry I hit return and posted my answer half way through writing it. Retain is the default behaviour in modern projects, it was only needed in older projects. Some people still use it out of habit, but these days don't use it. Just turn ARC on. – Abhi Beckert Jun 20 '14 at 03:05
  • yea when doing delegates or pointing to an object owned by someone else do I use week or assign? – rolling_codes Jun 20 '14 at 03:07
  • 1
    If using ARC, you'd use weak. If no ARC (older code) assign. – mc01 Jun 20 '14 at 03:10
  • 1
    You can use weak or assign in that case. Weak should be used most of the time, since it's safer. See the documentation for why. – Abhi Beckert Jun 20 '14 at 03:23
  • 4
    `atomic` does not guarantee thread safety. It only guarantees that the property will return coherent values in the face of threaded set/access. Thread safety is a much bigger problem than at the individual property level. See: http://stackoverflow.com/questions/588866/whats-the-difference-between-the-atomic-and-nonatomic-attributes – bbum Jun 20 '14 at 03:48
  • Also in ARC code you should use `assign` for value-based types such as boolean or integer: `@property(nonatomic, assign) NSUInteger counter;` – Artem Abramov Jul 13 '14 at 09:57
  • @ArtemAbramov really? I'm pretty surer value-based types will always do `copy`, no matter how the `@property` is declared. – Abhi Beckert Jul 14 '14 at 23:22
  • @AbhiBeckert You can't send `copy` to value based types, as they are not objects. If you try to type `@property(nonatomic, copy) NSUInteger counter` the compiler will clearly mark that as an error. – Artem Abramov Jul 16 '14 at 07:52
  • @ArtemAbramov I understand that, but NSUInteger will always make a copy, no matter what you declare it as. The definition of a "value" type is that it will always make a copy. – Abhi Beckert Jul 21 '14 at 15:37
0

Normally you @synthesize a property in your class implementation which creates a set function. You can write your own property set function, and do a mutable copy there. Problem solved...

- (void)setPropertyName:(propertyType *)newProperty {

  if (propertyName) [propertyName release];
  propertyName = [newProperty mutableCopy];
}
rolling_codes
  • 15,174
  • 22
  • 76
  • 112
8AxleEd
  • 49
  • 2