Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Good practice for disambiguating argument names versus instance variable names in Objective-C

I run into a fairly common scenario in Objective-C where I pass in a variable to an init method and then want to assign it to an instance variable of the same name. However I have not found a way to scope the variables to clarify which is the value from the message argument and which is the instance variable.

Say I have some class such as the following:

@interface MyObject
{
    NSString *value;
}
- (id)initWithValue:(NSString *)value;
@end

In my implementation I want my init method to look something like this:

- (id)initWithValue:(NSString *)value
{
    self = [super init];
    if(self) {
        self.value = value;  // This will not work with instance variables
    }
}

I know of three solutions:

  1. Create a property, which allows calling self.value
  2. Rename my instance variable, such as _value
  3. Rename my init argument variable, such as initValue or argValue

I am not pleased with any of these solutions. Adding a property either makes the property publicly available on the interface or, if I use an extension, hides it from inheritors. I also do not like having different names for the variables or using an underscore, which perhaps comes from developing in other languages such as Java and C#.

Is there a way to disambiguate instance variables from message arguments? If not, is there a coding guideline in Cocoa for how to solve this problem? I like following style guidelines when appropriate.

Update

After thinking about how to do this in C, I came up with the solution of self->value. This works, but it produces a compiler warning that the Local declaration of 'value' hides instance variable. So this is not a satisfactory solution either since I have a zero-warning goal.

like image 789
David V Avatar asked Jan 05 '12 18:01

David V


3 Answers

For setters (and by extension initializers), I believe the convention is to prefix the parameter name with new:

- (void)setCrunk:(Crunk *)newCrunk;
- (id)initWithCrunk:(Crunk *)newCrunk;

In general, I think the most common form I've seen is to call the parameter theCrunk, but Apple seems to recommend aCrunk.

like image 132
jscs Avatar answered Oct 20 '22 02:10

jscs


And changing the name to "inValue" is not a good idea? What you have here - your 'solution' is complex, especially with the accessors, etc of Obj-C 2. Since self.value and inValue are different things, they need different names.

Note that you can use

-(void)method1:(NSString*)value; 

in the header

and

-(void)method1:(NSString*)inValue; 

in the .m file.

like image 30
Tom Andersen Avatar answered Oct 20 '22 02:10

Tom Andersen


If you use only 1 the compiler will give you a warning.

You can combine 1 & 2 by using :

@synthesize value = _value;

If you want to hide your variable from the inheritors you can declare a empty named category and declare your property there.

For 3 you can use aValue for your argument.

like image 2
Stefan Ticu Avatar answered Oct 20 '22 01:10

Stefan Ticu