1

There was a case when not explicitly initilizing a local CGFloat to 0 would result the variable holding garbage:

-(void)foo
{
   CGFloat aFloat;
   NSLog(@"float:%f", aFloat);
   aFloat = 70;
}

[self foo];
[self foo];

Output:

float:0
float:70

So it really should print 0 both times, but since I didn't explicitly initialize the float to 0, it contained garbage the second time around. My question is, does this apply to objects as well? Is there a difference for local variables between these two options:

1. NSObject *object;
2. NSObject *object = nil;
Snowman
  • 31,411
  • 46
  • 180
  • 303

3 Answers3

3

A pointer is initially nil if it is an ivar. (It is an ivar if you have declared it in the @interface part of your class.) If the pointer is a local variable (you declared it in a method) it will contain garbage. It is best practice to always assign something right away.

Update: As pointed out in the comments by omz, if you are using ARC, your pointers are also nilled if they are local variables.

Johan Kool
  • 15,637
  • 8
  • 64
  • 81
  • Addition: If you're using ARC, _all_ objects will be initialized as `nil`, not just ivars. – omz Aug 06 '12 at 05:15
  • How does that work with ARC? If it contains garbage it will try to release garbage. – Daniel Aug 06 '12 at 05:16
  • 2
    The [ARC Release Notes](http://developer.apple.com/library/ios/#releasenotes/ObjectiveC/RN-TransitioningToARC/Introduction/Introduction.html%23//apple_ref/doc/uid/TP40011226-CH1-SW5) say that stack variables are implicitly initialized to `nil`, so something like `NSString *str; NSLog(@"%@", str);` will actually log `(null)` instead of potentially crashing. – omz Aug 06 '12 at 05:56
  • @omz Thanks for pointing that out, I've added it to my answer. – Johan Kool Aug 06 '12 at 07:05
2

it contained garbage the second time around

Actually it didn't contain garbage. It contained the same value that was written to that place in memory previously. It just happened that stack didn't got chance to get overwritten by any new value, so when you called foo the second time the aFloat variable got mapped to the same location.

For more specific description I highly recommend one of the best answers of all time.

Community
  • 1
  • 1
Bartosz Ciechanowski
  • 10,293
  • 5
  • 45
  • 60
1

Yes the same applies; the object pointer is a variable just like the float:

test.m:

#include <Foundation/Foundation.h>

@interface Foo : NSObject
{
    NSString *ivarString;
}

- (void)foo;
- (void)test;

@end

@implementation Foo

- (void)foo
{
    NSString *stackString;
    NSLog(@"stackString='%@', ivarString='%@'", stackString, ivarString);
    stackString = @"Hello";
    ivarString = @"World";
}

- (void)test
{
    [self foo];
    [self foo];
}

@end

int main(int argc, const char **argv)
{
    @autoreleasepool
    {
        Foo *foo = [[[Foo alloc] init] autorelease];
        [foo test];
    }
    return 0;
}

Output:

2012-08-06 06:52:36.123 test[15293:403] stackString='(null)', ivarString='(null)'
2012-08-06 06:52:36.126 test[15293:403] stackString='Hello', ivarString='World'

Note that this test project uses MRR, not ARC.

trojanfoe
  • 120,358
  • 21
  • 212
  • 242