仪器在以下代码中显示内存泄漏。我确保保持所有地方的保留计数。我还添加了自动释放池,还有内存泄漏。怎么解决这个问题?
代码块:
- (NSArray *)lookupAllForSQL:(NSString *)sql
{
sqlite3_stmt *statement;
id result = nil;
NSMutableArray *thisArray = [NSMutableArray arrayWithCapacity:4];
statement = [self prepare:sql];
if (statement)
{
while (sqlite3_step(statement) == SQLITE_ROW)
{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
NSMutableDictionary *thisDict = [NSMutableDictionary dictionaryWithCapacity:4];
for (int i = 0 ; i < sqlite3_column_count(statement) ; i++)
{
NSAutoreleasePool *poolInside = [[NSAutoreleasePool alloc] init];
if(sqlite3_column_type(statement,i) == SQLITE_NULL)
{
continue;
}
if (sqlite3_column_decltype(statement,i) != NULL &&
strcasecmp(sqlite3_column_decltype(statement,i),"Boolean") == 0)
{
result = [NSNumber numberWithBool:(BOOL)sqlite3_column_int(statement,i)];
}
else if (sqlite3_column_type(statement,i) == SQLITE_INTEGER)
{
result = [NSNumber numberWithInt:(int)sqlite3_column_int(statement,i)];
}
else if (sqlite3_column_type(statement,i) == SQLITE_FLOAT)
{
result = [NSNumber numberWithFloat:(float)sqlite3_column_double(statement,i)];
}
else
{
if((char *)sqlite3_column_text(statement,i) != NULL)
{
//result = [NSString stringWithUTF8String:(char *)sqlite3_column_text(statement,i)];
[thisDict setObject:[NSString stringWithUTF8String:(char *)sqlite3_column_text(statement,i)]
forKey:[NSString stringWithUTF8String:sqlite3_column_name(statement,i)]];
//[result release];
result = nil;
}
}
if (result)
{
[thisDict setObject:result forKey:[NSString stringWithUTF8String:sqlite3_column_name(statement,i)]];
}
[poolInside drain];
}
[thisArray addObject:[NSDictionary dictionaryWithDictionary:thisDict]];
[pool drain];
}
}
sqlite3_finalize(statement);
return thisArray;
}
乐器截图:
答案 0 :(得分:0)
我认为continue
声明可能是一个问题。由于continue
语句导致控制转到最近循环的下一个交互,如果条件(sqlite3_column_type(statement,i) == SQLITE_NULL)
为true
,控件将转到下一次迭代,而'poolInside'池将不会倒掉。所以我会用:
if(sqlite3_column_type(statement,i) == SQLITE_NULL)
{
[poolInside drain];
continue;
}
但是,这可能是您尝试解决泄漏的错误,因此来自@CodaFi的评论仍然有效。
为了完整起见
如果你们都看看poolInside
泄漏的后果,你可以看到这一行:
[thisArray addObject:[NSDictionary dictionaryWithDictionary:thisDict]];
每NSDictionary
次泄漏都会泄漏poolInside
。所以,这意味着返回的数组将包含泄漏的对象。此外,我怀疑泄漏嵌套的NSAutoreleasePool可能会导致在for循环中创建的对象也被泄露。我认为你发布的“仪器截图”显示了这种行为。
答案 1 :(得分:0)
我得到了解决方案。这个函数返回了一个NSArray,我没有正确发布。所以,所有这些变量都导致内存泄漏而不是这个功能。
This video让我理解这一点。