Re: Initializing an Array
Re: Initializing an Array
- Subject: Re: Initializing an Array
- From: Marcel Weiher <email@hidden>
- Date: Tue, 22 Jan 2002 21:51:12 +0100
On Tuesday, January 22, 2002, at 07:57 , Jeff Galyan wrote:
Here's an example of what I'm talking about:
/****************
* AppCrasher.h
****************/
#import <Foundation/Foundation.h>
@interface AppCrasher : NSObject
{
NSString *myString;
}
- (id)initWithString:(NSString *)aString;
- (void)dealloc;
There is not really any need to declare a dealloc method.
- (NSString *)methodOne;
- (NSString *)methodTwo;
- (NSString *)methodThree;
- (NSString *)methodFour;
- (NSString *)methodFive;
- (NSString *)methodSix;
@end
/*****************
* AppCrasher.m
*****************/
#import "AppCrasher.h"
@implementation AppCrasher
- (id)initWithString:(NSString *)aString
{
Missing [super init];
myString = [aString copy];
[myString retain];
Redundant retain.
Should probably assert that aString is non-nil because you're relying on
that later on.
return self;
}
- (void)dealloc
{
[myString release];
Missing [super dealloc];
}
- (NSString *)methodOne
{
// create a char* and send [myString getCString] with it
// do something with the C string
// return a new NSString
Since c-string manipulation can crash (instead of raising exceptions),
you should probably assert that myString is not nil.
}
- (NSString *)methodTwo
{
// same concept as methodOne
}
...
@end
/********************
* SomeClass.h
********************/
#import <Foundation/Foundation.h>
@interface SomeClass : NSObject
{
}
- (void)getCrashed:(NSString *)someString;
@end
/**********************
* SomeClass.m
**********************/
#import "SomeClass.h"
#import "AppCrasher.h"
@implementation SomeClass
- (void)getCrashed:(NSString *)someString
{
AppCrasher *myCrasher;
NSString *strOne, *strTwo, *strThree, *strFour, *strFive, *strSix;
myCrasher = [[AppCrasher alloc] initWithString:someString];
strOne = [myCrasher methodOne];
strTwo = [myCrasher methodTwo];
strThree = [myCrasher methodThree];
strFour = [myCrasher methodFour];
strFive = [myCrahser methodFive];
strSix = [myCrasher methodSix];
This is leaking an AppCrasher object.
}
@end
Then in some class, you allocate an instance of SomeClass and call
getCrashed with some string while iterating over a counter. After the
third
or fourth call to getCrashed, the app will crash. If you step through
in the
debugger (and remember, this is with optimization turned off),
Also, the optimization issues usually don't happen with instance
variables (my last info is actually 'always', but I don't know what the
compiler folks are up to)
you'll see a
new instance of myCrasher get created, then while you step through the
calls
to you'll see myString get initialized properly, then somewhere between
the
call to methodFour and methodSix (it varies), myString suddenly becomes
nil,
even though myCrasher has not been deallocated yet, so therefore, the
ivar
myString should not be getting sent a release message.
Once again, deallocating an object does not set instance variables
pointing to that object to nil. The fact that you're seeing
instance-vars getting zeroed means that something else is going on.
From your description so far, it sounds like you're stomping over memory.
Another option is that the object *containing* the instance vars is
getting deallocated and the memory belonging to it reused.
--
Marcel Weiher Metaobject Software Technologies
email@hidden www.metaobject.com
Metaprogramming for the Graphic Arts. HOM, IDEAs, MetaAd etc.