views:

576

answers:

5

I'm still working on my leaks problem and I don't know how to solve this one I have leaks on each arrayTmp addObject lines

NSMutableArray *arrayTmp= [[NSMutableArray alloc] init];


[arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"1", @"value", @"Value 1", @"name", nil]];
[arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"2", @"value", @"Value 2", @"name", nil]];
[arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"3", @"value", @"Value 3", @"name", nil]];
[arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"4", @"value", @"Value 4", @"name", nil]];
//add arrayTmp to an object to use later
[arrayTmp release];
arrayTmp=nil;

arrayTmp= [[NSMutableArray alloc] init];

[arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"1", @"value", @"other value 1", @"name", nil]];
[arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"2", @"value", @"other value 2", @"name", nil]];
//add arrayTmp to an object to use later
[arrayTmp release];
arrayTmp=nil;
...
+2  A: 
//add arrayTmp to an object to use later

That implies that you are shoving arrayTmp into an object and -retain'ing it. The code snipped is otherwise fine, but I'd bet the leak resides within that method.

Post the code for your method (which, btw, should really be -initWithLabel:value:listValue:webServiceFieldName: if you were to follow Obj-C's naming conventions) that stores away arrayTmp and the code that releases it.

In Instruments, you should be able to see the array instances using the Object Alloc instrument. Clicking through any one should give you a list of allocation/retain/release/deallocation events for that address. You can see the stack trace for any given event by expanding the "more info" pane at the right side of the window (via a little button at the bottom).

From the code below, your initializer sets the ivars, including the passed in tmpArray as such:

    self.label = plabel;
    self.valueIndex = pvalueIndex;
    self.listValue = plistValue;
    self.webServiceFieldName = pwebServiceFieldName;

However, I don't see a -dealloc method.

Assuming your properties are declared with either retain or copy, your dealloc should look like:

- (void) dealloc
{
    [label release];
    [listValue release];
    [webServiceFileName release];
    [super dealloc];
}
bbum
A: 

Here the code of my Filter class

@implementation Filter

@synthesize label;
@synthesize valueIndex;
@synthesize listValue;
@synthesize webServiceFieldName;

-(id) initWithLabel:(NSString *)plabel AndValue:(int)pvalueIndex AndListValue:(NSMutableArray *)plistValue AndWebServiceFieldName:(NSString *)pwebServiceFieldName {

self = [super init];

if (self != nil) {
 self.label = plabel;
 self.valueIndex = pvalueIndex;
 self.listValue = plistValue;
 self.webServiceFieldName = pwebServiceFieldName;

}
return self;
}

@end
Mathieu
+1  A: 

You have to make sure you release your synthesized member variables when you dealloc this object -- it will not be done for you automatically. E.g.:

- (void)dealloc
{
    [label release];
    [listValue release];
    [webServiceFieldName release];

    [super dealloc];
}
fbrereto
You forgot [super dealloc]; at the end.
bbum
yep; fixed. Thanks!
fbrereto
A: 

Ok I made these changes but I still have dozen of leaks on these lines Here is a sample of my code

-(id)initSearchFilters{
    self = [super init];


    if ( self ) {

    //init the search filters array
    self.searchFilters = [[NSMutableArray alloc] init];
    SearchCriteria *searchCriteriaTmp;
    Filter *filterTmp1;
    Filter *filterTmp2;
    NSMutableArray *arrayTmp= [[NSMutableArray alloc] init];

    //Price Range
 arrayTmp = [[NSMutableArray alloc] init];

 [arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"any", @"value", @"any", @"name", nil]];
 [arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"100", @"value", @"$100", @"name", nil]];
 [arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"200", @"value", @"$200", @"name", nil]];
 [arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"300", @"value", @"$300", @"name", nil]];
 [arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"400", @"value", @"$400", @"name", nil]];
 [arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"500", @"value", @"$500", @"name", nil]];


 filterTmp1 = [[Filter alloc] initWithLabel:@"Minimum Price" AndValue:0 AndListValue:arrayTmp AndWebServiceFieldName:@"price_min"];
 filterTmp2 = [[Filter alloc] initWithLabel:@"Maximum Price" AndValue:0 AndListValue:arrayTmp AndWebServiceFieldName:@"price_max"];
 searchCriteriaTmp = [[SearchCriteria alloc] initWithFilter1:filterTmp1 AndFilter2:filterTmp2 AndLabelSearchCriteria:@"Price Range" AndEnabled:NO];
 [self.searchFilters addObject:searchCriteriaTmp];
 [arrayTmp release];
 arrayTmp=nil;
 [filterTmp1 release];
 filterTmp1=nil;
 [filterTmp2 release];
 filterTmp2=nil;
 [searchCriteriaTmp release];
 searchCriteriaTmp=nil;

 //Item
 arrayTmp = [[NSMutableArray alloc] init];

 [arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"1", @"value", @"item 1", @"name", nil]];
 [arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"2", @"value", @"item 2", @"name", nil]];
 [arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"3", @"value", @"item 3", @"name", nil]];
 [arrayTmp addObject:[NSDictionary dictionaryWithObjectsAndKeys:@"4", @"value", @"item 4", @"name", nil]];

 filterTmp1 = [[Filter alloc] initWithLabel:@"Item" AndValue:0 AndListValue:arrayTmp AndWebServiceFieldName:@"item"];
 searchCriteriaTmp = [[SearchCriteria alloc] initWithFilter1:filterTmp1 AndFilter2:nil AndLabelSearchCriteria:@"Item" AndEnabled:NO];
 [self.searchFilters addObject:searchCriteriaTmp];
 [arrayTmp release];
 arrayTmp=nil;
 [filterTmp1 release];
 filterTmp1=nil;
 [searchCriteriaTmp release];
 searchCriteriaTmp=nil;
    }
    return self;
}


And my search criteria class

-(id)initWithFilter1:(Filter *)pFilter1 AndFilter2:(Filter *)pFilter2 AndLabelSearchCriteria:(NSString *)pLabelSearchCriteria AndEnabled:(BOOL)pEnabled{

self = [super init];

if (self != nil) {
 self.filter1 = pFilter1;
 self.filter2 = pFilter2;
 self.labelSearchCriteria = pLabelSearchCriteria;
 self.enabled =pEnabled;
}
return self;
}

- (void)dealloc
{
[filter1 release];
[filter2 release];
[labelSearchCriteria release];
[super dealloc];
}
Mathieu
I call initSearchFilters several times so I think it's due to the line self.searchFilters = [[NSMutableArray alloc] init];But where can I place this line so it's called only one time?
Mathieu
Ok I solved it it was due to the several calls to initSearchFilters
Mathieu
A: 

In the above code the lines that allocate a SearchCriteria and call initSearchFilters will set the retainCount of the result to 1. When you then add that object to self.searchFilters via addObject the retainCount is then bumped to 2. At that point you need to call [searchCriteriaTmp release] to set the retainCount back to 1. When self.searchFilters is destroyed the retainCount will then be 0, and the object will be deallocated. Without the additional call to release the retainCount will always be 1, and the object will never deallocate, causing the leak.

fbrereto