Reputation: 337
I've used leaks to locate a memory leak that is related to SBJsonParser tho I don't understand why I'm getting it? I was hoping someone might be able to shed some insight. Leaks reports that the leak is coming from a method called objectWithURL. This method is called from a method called downloadJSONFeed. I have shown both below.
Any insight appreciated.
- (id) objectWithUrl:(NSURL *)url
{
SBJsonParser *jsonParser = [SBJsonParser new];
NSString *jsonString = [self stringWithUrl:url];
// Parse the JSON into an Object
return [jsonParser objectWithString:jsonString error:NULL];
}
- (void) downloadJSONFeed
{
//set up query
NSString *lat = [NSString stringWithFormat:@"%f", ad.locationManager.location.coordinate.latitude];
NSString *lon = [NSString stringWithFormat:@"%f", ad.locationManager.location.coordinate.longitude];
NSString *postValues = [NSString stringWithFormat:@"http://vivid-wind-8436.herokuapp.com/bathrooms/nearby.json/?lat=%@&lon=%@",lat, lon];
//get server response
id response = [self objectWithUrl:[NSURL URLWithString:postValues]];
//store in dictionary
NSDictionary *dictionary = (NSDictionary *)response;
//array for json data
NSMutableArray *jsonData = [[NSMutableArray alloc] init];
for (NSDictionary *dict in dictionary)
{
Bathroom *bathroom = [[[Bathroom alloc] init] autorelease];
bathroom.name = [dict objectForKey:@"name"];
bathroom.street = [dict objectForKey:@"street"];
bathroom.city = [dict objectForKey:@"city"];
bathroom.state = [dict objectForKey:@"state"];
bathroom.postal = [dict objectForKey:@"postal"];
bathroom.country = [dict objectForKey:@"country"];
bathroom.accessibility = [dict objectForKey:@"access"];
bathroom.gendered = [dict objectForKey:@"bathroomtype"];
bathroom.availability = [dict objectForKey:@"avail"];
bathroom.directions = [dict objectForKey:@"directions"];
bathroom.comment = [dict objectForKey:@"comment"];
bathroom.distance = [dict objectForKey:@"distance"];
bathroom.lat = [dict objectForKey:@"lat"];
bathroom.lon = [dict objectForKey:@"lon"];
[jsonData addObject:bathroom];
}
//now sort array by distance
NSSortDescriptor *sortDescriptor;
sortDescriptor = [[[NSSortDescriptor alloc] initWithKey:@"distance" ascending:YES] autorelease];
NSArray *sortDescriptors = [NSArray arrayWithObject:sortDescriptor];
NSArray *sortedArray;
sortedArray = [jsonData sortedArrayUsingDescriptors:sortDescriptors];
//dataArray = [[NSMutableArray alloc] init];
//add objects to data array
[dataArray addObjectsFromArray:sortedArray];
//release json data
[jsonData release];
}
Upvotes: 2
Views: 715
Reputation: 42163
[SBJsonParser new]
equals to [[SBJsonParser alloc] init]
. By calling this objectWithUrl
owned the created SBJsonParser
object, so you need to release it within this method:
SBJsonParser *jsonParser = [[SBJsonParser new] autorelease];
You can also:
- (id)objectWithUrl:(NSURL *)url
{
SBJsonParser *jsonParser = [SBJsonParser new];
NSString *jsonString = [self stringWithUrl:url];
// Parse the JSON into an Object
id jsonObject = [jsonParser objectWithString:jsonString error:NULL];
[jsonParser release];
return jsonObject;
}
Refer to Another iPhone Memory leak issue.
Upvotes: 1
Reputation: 62686
Yup. Need to release the parser. Store the parse in a stack var, release the parser, then return.
Upvotes: 0
Reputation: 3154
Sorry it's been a while since I coded in Objective-C but does this work?
SBJsonParser *jsonParser = [[[SBJsonParser alloc] init] autorelease];
Upvotes: 0