Objective-C Properties in iPhone Development - iphone

Whats the difference between a property and an instance variable in Objective-C. I need to understand this in OOP terms. Is a property declaration just a convenience wrapper (with #synthesize in the implementation) for accessing instance variables?
thanks,
codecowboy.

Properties and ivars are two completely different things.
And instance variable is a variable stored inside the object, so each instance has its own. It is referenced by pointer addition relative to the object pointer/self (slightly indirected for the modern runtime, but functionally equivalent). ivars are generally internal to a class, and by default can only be accessed by the class and its descendents (#protected). Within methods they are available with no qualification, otherwise they can (but rarely are, ad usuaually should not) be accessed via indirection, eg obj->ivar.
A property defines a getter and setter (the setter is optional) interface. That's all it does. It defines two public methods:
- (TYPE) propname;
- (void) setPropname: (TYPE) newPropname;
These are defined as methods exactly as if you declared them like that, no more, no less. These methods are called either with the normal syntax ([obj propname] and [obj setPropname:n] or using the modern dot notation (obj.propname or obj.propname = n). These two options are syntactically different only, they behave identically, and you can use dot notation whether the methods are declared with #property or declared manually as above.
You must then implement the methods in the implementation, either by writing the methods yourself, by using #synthesize, or by handling the missing method dynamically.
Properties may be backed by an ivar (named the same or named differently (my preference to avoid confusion)), or they may not. They may store their value elsewhere, or they may calculate it from other data.
For example, you might have:
#property (nonatomic, readonly) NSString* fullname;
and then implement - (NSString*) fullname to return the concatenation of firstname and lastname.

I think you are pretty much there. The #property and #synthesize make the accessor declarations and implementation for the already declared ivar. You have various attributes you can define on the #property too giving you control over how it is generated to make it appropriate for the ivar
Have a look at "Objective C 2.0 Declared Properties"

The difference between Property and Instance ivar is, the variable which make as Property that can be visible in another Class whereas for accessing the iVar or instance you need to create the Object of that class and then you can access.
and With use of #synthesize compiler will generate the setter and getter for that property.
-(TYPE)name;-getter Method
-(void)setName:(TYPE)aName; setter Method

Related

In Objective-C, when should I use property and when should I use instance variable?

I'm not familiar with the program language which has both property and instance variable.
So I don't know good ways to use property and instance variable.
Now I use only properties in my Objective-C code and I don't use any instance variables.
Do I need to use instance variable?
Or using only property is the best practice for Objective-C?
#interface ViewController : UIViewController
{
// instance variable
#public
int a;
}
// property
#property(nonatomic, strong) NSString *b;
#end
The basic difference between variable and property is that, you can give attributes to property. You can not give any attributes to variable.
So, if you wish to have any specific behavior like retaining the variable, accessing it atomically, have access out side the class, you should go for the properties.
If you simply want to access the variable with in the class and no special behavior is attached to that variable, no need to access it via property. You can directly use variable itself. It will improve the performance also.
There are some advantages a #property has over an ivar:
Memory management : Behind the scenes it will create a setter which creates the variable with correct memory management. It will save you some headaches because you can easily see how the memory management is done (strong/weak and retain/copy/assign).
Accessibility from other classes: if you declare your #property in the .h and #synthesize it in the .m you ivar will be public readable and writeable. You can prevent this with a privat class extension. You even can declare a #property public readonly and declare them internally readwrite via a privat class extension.
Eg: a private property
// [In the implementation file]
#interface MyClass ()
#property (nonatomic, retain) NSMutableArray* someData; // private!!
#end
#implementation MyClass #synthesize someData
#end
Custom getter and setter: If you like you can still write custom getter and setters and you can even just write a getter or setter and let the other one automatically #synthesize. And you can write custom logic into such a getter and setter e.g. you can reload a tableview after a #property has changed.
Automatic Key-Value-Observing (KVO) compliant: If you use or planning to use KVO you get it basically for free by just declaring the property. Nothing else need to be done!
Dot notation: You can access getter and setter via dot notation if you have the #property.
self.myIvar = (id) someThing;
[array addObject:self.myIvar];
If you need you iVar to be public it is simpler to write one #property than writing a getter and setter for a iVar
With a #property you do not need to declare in iVar (in iOS and 64bit Mac Os X applications). You can do it via the #synthesize:
#synthesize myiVar = _myIvar;
Use properties everywhere. Don't even declare instance variables, but synthesize them like this: #synthesize myProperty = _myProperty in order to differentiate them from property names. Properties are good way to cope with memory management as well. The only place you must use the synthesized instance variable is in the dealloc method.
The advantages of the properties are a lot:
- The accessor methods define how will you get and set the value of your instance variable.
- You can customize the accessor methods (for example to lazy instantiate an ivar or do something when a setting a new value like setNeedsDisplay.
- You don't cope with memory management when setting a new value - the setter takes care for releasing/retaining (depending how have you declared the property - retain/copy/assign/strong.
- Some multithreading stuff with the atomic/nonatomic attributes
- You can take advantage of the KVO, when using properties
- And least, but not last - don't worry about performance issues if you have concernes that every time a getter or a setter is called...
A #property is an instance variable that has had some semantic sugar applied to it, to help expose it to the outside world (usually), and to help avoid writing boilerplate code for getting and setting it.
though properties are made generally when you need to access some variable outside of the class, mean getter n setter, but in objective C, an additional need to make property is that the memory management goes on compiler ends, so if you are using some object, not primitive data types, then you should use property and synthesize it, and then release in dealloc if you are using manual reference counting. but again the main objective to make properties it to access some iVar outside the class like passing parameters from one class to other etc.
If you #synthesize a #property, you will have access to a get and a set method, which are very convenient. You can also define how the setter will behave (retain, assign, copy) if it's nonatomic or atomic and if it's read only. If you don't specify anything (aka you don't synthesize the property) the ivar won't be visible outside of the class by default, but you can achieve this by using #public. Logically you can also define them as #private or #protected .
Normally I #synthesize a #property because I want to have access to the ivar from the outside of the class and also because I want a getter and setter methods.
The general opinion is that you should use properties whenever possible. If you're still in doubt, here is Apple's recommendation:
In general, you should use accessor methods or dot syntax for property access even if you’re accessing an object’s properties from within its own implementation, in which case you should use self.
...
The exception to this rule is when writing initialization, deallocation or custom accessor methods
...
You should always access the instance variables directly from within an initialization method because at the time a property is set, the rest of the object may not yet be completely initialized
Read the whole document here for a better understanding of the subject.
As for performance issues, for most apps the gain is insignificant. Read this for a very detailed description.

What exactly is a property in Objective C ? What is the difference between a property and an instance variable?

I am very much confused between instance variables and property. I have read number of posts regarding this but still i am not clear about it.
I am from JAVA background and what i infer from objective C documentation is that a property is similar to JAVA BEAN CLASS (one having getter and setter of instance varibles). A property can accessed from other classes through its getter and setter methods while an instance variable is private and cannot be accessed from other classes.
Am i right in thinking in this direction ?
The parallel with Java is very good. The only difference is that Objective C provides a way to access a property as if it were a variable, and Java does not. The other difference is that in Objective C you can synthesize properties, while in Java you need to write your getters and setters manually.
Property is a "syntactic sugar" over a getter method or a pair of a getter and a setter methods. Properties are often (but not always) backed by an instance variable, but they can be implemented in any way that you can implement a parameterless instance method.
Ok, instance variable and property is far away from each other. instance variable is a state of object and property is a assecor method(getter/setter) of that state(instance variable).
So whenever you create an property in header file. compiler convert those property in to accessor method. suppose you declared property - #property(nonatomic, assign, readwrite) NSString *name;
So compiler will be converted those in to
-(NSString *)name;
-(void)setName:(NSString *)name;
And then for definition for accessor method there is two way.
manually - use dynamic in implementation file(.m) and then give the definition of accessor method by doing this you won't get any warning.
Let compiler do the job - this can be done by synthesizing property e.g synthesize name;. so now compiler will generate the definition for the accessor method for you.
Hope it helps ;)
I know this subject has been beat to death here ... but some seem to be focusing on the technical details, whereas I wanted mention something along the lines of the BIG PICTURE ...
Think of properties as kind of first-class ivars. Both properties and ivars may model attributes of an object ... but an ivar gets special attention if you go ahead and set it up as a property. Basically, you should an attribute as a property (as opposed to an ivar) if you feel it needs getter / setter methods. Dot notation makes for very readable code. This may help in deciding when to declare a variable as a property as opposed to simply using a regular ivar.
A property in objective c is in fact the setter and getter methods that make it possible to access an attribute in a class from outside of it. So when you declare for example
#interface example:NSObject{
NSString *variable;
}
#property(readwrite, assign) NSString *variable;
#end
#implementation
#synthesize variable;
#end
You are in fact declaring the methods
-(NSString *)getVariable;
-(void)setVariable(NSString *)value;
And you can access then by using the point notation and the name of the property, like
instance.variable = something;
something = instance.variable;
The primary difference between instance variable and property is that for properties, the compiler will automatically generate a getter/setter method pair. For instance:
#property (nonatomic) int value;
will generate:
-(void)setValue:(int)i
{
value = i;
}
-(int)value
{
return self->value;
}
given #synthesized.
If you crab a book on Objective-C 1.0, you'll notice that this feature isn't available. This is a new feature in 2.0, also known as the dotted syntax. It's introduced mainly because the complicated getter/setter syntax.
The benefit of this feature is that even though you have the compiler automatically declared the pair for you, you can still manage to override it. For instance, you can still have -(void)setValue:(int)i declared as a method of your class, and override the behavior. This is useful in scenarios of validation, such as you want to put a limit on the range of value.
As far as Java is concerned, Objective-C actually do have #public instance variable syntax, but it's a habit not to use it. It's sort of similar to Java's concept of protecting a private variable through getter/setter. But its primary objective-c is to override getter/setter and minimize syntax.
Now this is just a preview, refer to http://cocoacast.com/?q=node/103 or some objective-c 2.0 books if you wanted to know more.
Well, maybe it was not clear that a property does not need an instance variable.
You can define a read-only property based on any calculation on instance variables or any other variables in the scope. The issue here is that you must manually code the getter.
#interface person:NSObject{
NSDate *birthDate;
}
#property(readonly) int age;
#end
#implementation
-(int) age{
// return calculated age based on birthDate and today;
}
#end
The name of the property does not need to be the same as the instance variable.
#synthesize myProperty = myVar;
I found this amazing thread which clearly explains each and evrything about properties.
http://www.iphonedevsdk.com/forum/iphone-sdk-tutorials/7295-getters-setters-properties-newbie.html
Thank you all for your responses.

When do I need to have both iVar and a property?

I see some examples sometimes would declare a property as well as variable other times they do not .e.g. some time I see code like this
#interface Test : NSObject
{
UIProgressView* _progressView;
}
#property (nonatomic,retain)UIProgressView* progressView;
#end
at other times I will come across
#interface Test : NSObject
#property (nonatomic,retain)UIProgressView* progressView;
#end
Why what are the reasons ? I am learning and almost always use property and variable both.
I have used UIProgressView just as example.
Using ivars instead properties is only useful if you want #protected access (access from subclasses only), or support the old runtime (which required both).
It depends whether the property is synthesized against an iVar or derived in some other way (or against another iVar).
IF we have an instance of the class - i.e:
Test *myTest = [[Test alloc] init];
Then basically the property declaration
#property (nonatomic,retain)UIProgressView* progressView;
is telling anyone interested in using the interface that they can access the following two functions on an instance of this class:
[myTest progressBar];
[myTest setProgressBar:aProgressBar];
And objective C also lets you use shorthand notation:
myTest.progressBar =
xxx = myTest.progressBar
which does exactly the same thing.
It is not necessary for these two methods to be implemented via an iVar of the same name as the property, or even via an iVar at all (they could do even do a database fetch or derive the value).
If you #synthesize the property (which means you want the precompiler to generate the above methods for you) and don't explicitly specify an iVar on the #synthesize directive, then the methods described above will automatically be generated (due to the synthesize method) to set or get the value to/from an iVar of the same name as the property (and the implementation will include retain/release logic depending on the property directive.
If you don't #synthesize the property then you provide your own implementation and it can be anything you want. It is also possible to #synthesize the property but include a directive to use a different iVar in the method definition:
#synthesize progressBar=someOtheriVar;
in which case you will not see an iVar of the same name as the property in the header file either.

Basic objective C variable declaration

I am puzzled by how is variable declared in objective C.
1: I see #property and #synthesize statement being used. My question regarding that is, what are these 2 statement for? Why are they always used together? I guess #synthesize is a shortcut to create the getter and setter?
2:Say, I want to declare an NSMutableArray that would be only be accessible inside the class that was declared in. I have to perform myArray = [[NSMutableArray alloc] init] before using the addObject method to write something to it. When do I release the array then?
3:Is there a different way to declaring a variable that is only accessible only at the class it was declared to being accessible at all classes?
4:Similar to question 2, but now the variable is an NSString. Why I don't have to alloc & init it to share the same variable within its own class? Whats the different between self.myString = #""; to myString = #"";
Thanks a lot.
For your first question:
#property (nonatomic, retain) NSString * someProperty;
This declares a property of the class. It becomes part of the public contract of the class but still lacks something important - actual implementation
#synthesize someProperty;
This is compiler sugar, its creates a getter and setter method for your property. To wit, this is the implementation that is needed in order to actually use your property in your class and from other classes.
You will in almost all situations, always have a #synthesize for each #property you declare.
For your second question:
You are correct about how to initialize your array property. In order to release it you would do the following in your classes dealloc method:
- (void) dealloc {
self.myarray = nil;
[super dealloc];
}
This effectively releases the array (assuming you declared your property with the keyword retain).
And for your last question:
Properties of a class are always available from other classes. In order to create a globally accessible variable you would declare it as static.
Ad 1: a property is a construct to control access an ivar (usually private) by getters and setters. Actually, a property doesn't even have to have a supporting ivar. Yes, #synthesize generates getter and setter (and ivar).
Ad 2: You release it when you don't need it anymore. When that is depends on the logic of your code.
Ad 3: If I understand that correcttly, you want #private ivars. Normally, ivars are protected, i.e. only accessible inside the class or in derived classes. Private ivars are only accessible inside the class itself. Properties are publicly accessible.
Ad 4: myString = #"" writes to the ivar directly, while self.myString = #"" uses the property setter.
You need to get a text on Objective-C or find an online tutorial -- it's a sufficiently arcane language that you can't hope to pick it up in dribs and drabs.
There are variables and there are properties -- two different things that intersect somewhat.
You can declare plain old instance variables the same way as in C/C++, more or less:
NSArray* myArray;
eg, placed in the {} enclosed section of the #interface.
But you can also have a PROPERTY, which you declare by saying #property in the #interface declaration (after the closing }). A property has a getter method -- by default called myProperty -- and a putter method -- by default called setMyProperty. If myProperty is the same name as one of your instance variables then you can use #synthesize to automatically create these methods.
Note that properties may be automatically retained when the default setter method is used. This is fairly convenient in terms of managing storage.
But managing storage is a big topic, one that you MUST read some good tutorial on -- we can't explain it in a few paragraphs.
1) #property declares a publicly accessible variable and associated getter and setter. #synthesize causes the compiler to automatically generate the definition (code) of the getter and setter.
2) You would declare the NSMutableArray in your class declaration, in the header file. You would initialize the variable in your init method, and you would release the variable in your dealloc method.
3) The variables created using #property are public. The variables defined in your class declaration (using #interface in the header file) can be declared as private to that class, using the #private keyword.
John, these questions are pretty basic. You would probably get a lot out of the Objective-C Programming Intro here ( http://developer.apple.com/library/ios/#documentation/Cocoa/Conceptual/ObjectiveC/Introduction/introObjectiveC.html#//apple_ref/doc/uid/TP30001163 ).

Different between self.myIvar and myIvar?

What's the difference between referring to an instance variable in an objective-c class as this:
self.myIvar
and
myIvar
if it's been declared as a property in the header and synthesized?
If you refer to self.myVar, it will use the #property declared in your header file.
For example
#property(nonatomic, retain) Class *myClass;
If you have
myClass = [ [ Class alloc ] init .... ];
Retain Count will be 1
But if you use
self.myClass = [ [ Class alloc ] init .... ];
Retain Count will be 2 because of the retain property.
It's the same if you set setter || getter method in the #property.
What's the difference between referring to an instance variable in an objective-c class as this:
self.myIvar
and
myIvar
if it's been declared as a property in the header …
Simple: The former does not refer to an instance variable.
It refers to a property named myIvar. Likewise, the latter refers to an instance variable and not a property.
The property is, of course, misnamed, because a property and an instance variable do not necessarily have anything to do with each other, and indeed a property does not even need to be backed by an instance variable.
Attempting to access self.myIvar is exactly the same as sending self a getter message for the property. That is, these two statements:
foo = self.myIvar;
foo = [self myIvar];
are exactly the same.
Likewise, attempting to assign to self.myIvar is exactly the same as sending self a setter message. These two statements:
self.myIvar = foo;
[self setMyIvar:foo];
are exactly the same.
By comparison, referring to the instance variable myIvar (no self.):
foo = myIvar;
myIvar = foo;
is exactly that: accessing a variable; nothing more.
This means a lot.
The accessors, particularly the setter, tend to have side effects. For example, if the property is declared as retain, a synthesized setter for it will release the old value of the property and retain the new value. Likewise, if the property is declared as copy, a synthesized setter will release the old value and make a copy of the new one.
Since an assignment to a property:
self.myProperty = foo;
is an accessor message, that “assignment” will cause the old value to be released and the new value to be retained/copied.
An assignment to a variable:
myIvar = foo;
being nothing more than an assignment to a variable, will not do that. If you owned the old value of myIvar, you just leaked it, and if you don't already own the new value, you still don't own it, which means it will probably die while you're still holding onto it, leading to a crash later. (See the Memory Management Programming Guide.)
Despite the two looking similar, they are very, very different.
As a general rule, you should use your properties everywhere except init methods and the dealloc method, and directly access the instance variables (where you have instance variables) in those methods. (Again, accessors may have side effects; you're likely to not want those side effects in a half-initialized or half-deallocated object.)
… and synthesized?
That doesn't matter. #synthesize is just one of three ways of telling the compiler how the property's accessors are implemented:
#synthesize: Compiler, you implement them.
#dynamic: Don't worry about it, compiler; my superclass will dynamically supply the accessors at run time. (Most common in subclasses of NSManagedObject.)
- (Foo *) myProperty { … } / - (void) setMyProperty:(Foo *) newFoo { … }: Here are my implementations of the accessors.
Failing to do one or more of those things for a property will get you a warning from the compiler and probably some run-time exceptions, because you never actually stated an implementation for the accessors that (by declaring a #property) you declared the instances would have.
The difference is that ivar is just a variable pointing to a location in memory, whereas self.ivar calls the setter (in the case of self.ivar = x) and getter (for x = self.ivar) methods. IE, under the hood, the self.ivar in these statements gets translated into [self setIvar:value] and [self getIvar] respectively . These methods can then handle things like retain/release and any class-specific behaviour on your behalf, and in fact do so by referencing ivar directly. The #synthesize keyword automatically generates these getter and setter methods for you to cut down on boilerplate code.
So, ivar is a location in memory where your object can store something, and self.ivar wraps class methods around that location in memory to manage access to it. Note that when initializing an object it is usually preferable to set the ivars directly to avoid possible strange behaviour with not-quite-fully-formed objects.
Without the self. part you'll be accessing/assigning the actual data member of the class, without going through the getter/setter generated by #synthesize (or you can write your own getter/setter if you need something more fancy than the default behavior).
Note that in those custom accessors you'd pretty much have to omit the self. part to avoid endless recursion, e.g. if you have a string property called s, a setter could be (this is similar to what is generated when you do #synthesize, by the way):
-(void)setS:(NSString *)newVal
{
if(newVal == s) return;
[s release];
s = [newVal retain]; //if you use self.s here, setS will be called again
}
self.ivar
calls a property method that you can later change or add to, and that might do some memory management as well. For instance, you could make setting self.ivar also change ivar2, increment ivar3, bounds check ivar4, send a message to object5, release object6, play sound7, etc.
ivar
just reads or writes some number of bits in memory.