0

The recommended practice is to use property, including private ones through class extension instead of ivar (except in init and dealloc) in the post ARC environment.

Aside from it being a recommended practice, what are the main drawbacks in someone using ivar instead of property? I am trying to convince some folks to make the switch but some have argued ivar works just as well and faster. So I would like to collect good solid arguments rather than giving soft statements such as "it's better, more consistent, etc."

Boon
  • 40,656
  • 60
  • 209
  • 315

3 Answers3

1

There is no right answer to your question, just opinions. So you'll get varying answers, here's one to add to your collection :-)

Using private properties is is not recommended practice, it is largely a fad. :-)

A public property is part of the encapsulation of the class - how a property (or method) is implemented is not relevant to the user, only the behaviour.

A class does not need to hide how it is implemented from itself!

So the only use cases for private properties is where they provide some behaviour in a convenient way to the implementation of the class, not to hide that behaviour.

A private property with the copy attribute may be convenient if the class is, say, obtaining mutable strings from another class and needs to preserve their current values.

If the class wishes to lazily construct a value if it is needed but keep it after that time then a property can handle that conveniently. Of course a method or function can as well as a property is after all just a method call.

To make the choice think convenience/code design rather than encapsulation as you do for public properties. And most of the time you'll probably just use instance variables, just as you just use local variables.

HTH

CRD
  • 52,522
  • 5
  • 70
  • 86
  • It is recommended practice according to Apple's encapsulation docs. "It’s best practice to use a property on an object any time you need to keep track of a value or another object". Is this outdated, or not referring to 'private' properties? – Logan May 24 '14 at 23:46
  • The reference is primarily about *encapsulation*, and earlier it says "Given that one of the primary principles in object-oriented programming is that an object should hide its internal workings behind its public interface, it’s important to access an object’s properties using behavior exposed by the object rather than trying to gain access to the internal values directly." It does not rule out private properties but does cover declaring instance variables in the `@implementation` a feature which was introduced to Obj-C *after* properties... – CRD May 25 '14 at 01:56
0

There is not much difference in terms of performance. In reality, properties are instance variables with the accessors generated. So the reason why you want to do properties is because the code to generate the KVO notifications and the setter/getter methods are generated to you. So you have less time doing repetitive code on all your classes.

J2theC
  • 4,412
  • 1
  • 12
  • 14
  • Is there ever a need to KVO a private property? Also, why do you need setter/getter assuming you don't need custom behavior? – Boon May 24 '14 at 22:57
0

There are a few cases where using a private property is better or required over using an instance variable:

  1. KVO - Since KVO requires getter/setter methods to do the work, you need a property (technically just the methods). Using KVO on a private property probably isn't too common.
  2. Lazy loading or other "business logic" around the value. Using a property with custom setter/getter methods allows you to apply lazy loading and/or other logic/validation around the value.
  3. Access to the value inside a block using a weak reference.

The last point is best covered with an example. As many people know, under certain conditions you can create a reference cycle in a block and this can be broken using a weak reference to self. The problem is that you can't access an ivar using the weak reference so you need a property.

__weak typeof(self) weakSelf = self;
[self.something someReferenceCycleBlock:^{
    weakSelf->_someIvar = ... // this gives an error
    weakSelf.someProperty = ... // this is fine
}];

Basically, use an ivar if none of these points will ever apply. Use private properties if any of these may apply over the lifetime of the class.

rmaddy
  • 314,917
  • 42
  • 532
  • 579
  • 1
    Just wanted to comment that if you convert `weakSelf` to `strongSelf` you can set Ivars via `strongSelf->_someIvar`. – Logan May 24 '14 at 23:52
  • Excellent suggestion that I hadn't considered. Thanks. – rmaddy May 25 '14 at 00:40
  • @rmaddy, Is there ever a need to KVO a private property? – Boon May 26 '14 at 07:17
  • There may not be a need for KVO but there may be a need to know when a value changes and this is best done with a custom setter for the private property. – rmaddy May 26 '14 at 16:34
  • So one can argue that when there is a need for KVO then use property instead of ivar. For normal usage, ivar is just fine, correct? – Boon May 26 '14 at 20:21
  • My answer basically says "use an ivar unless you need a property for the reasons I listed". Or, use properties always. It's up to you. – rmaddy May 26 '14 at 21:07