2011-05-13 106 views
2

我使用下面的函数来把我的XML的每个“设施”节点在NSMutable阵列:自动释放池和内存管理

-(void) grabXML { 

    NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init]; 

    CXMLDocument *doc = [[[CXMLDocument alloc] initWithData:data options:0 error:nil] autorelease]; 

    NSArray *nodes = [[doc rootElement] nodesForXPath:@"//facilities" error:nil]; 

    for (CXMLNode *itemNode in nodes) 
    {    
     for (CXMLNode *eventNode in [itemNode children]) 
     {   
      if ([[eventNode name] isEqualToString:@"facility"]) { 

       [content addObject:[eventNode copy]];    

      } 

     } 
    } 

    loading = FALSE; 
    [table reloadData]; 

    [pool release]; 

} 

注意,游泳池是必要的,因为我叫grabXML方法在一个单独的线程中。

使用仪器我可以看到下面的行产生泄漏

[content addObject:[eventNode copy]]; 

如果我将其更改为

[content addObject:eventNode]; 

我不能稍后访问XCMLNode(它似乎为空)。

我能避免泄露把这个在我的dealloc方法:

for (CXMLNode *node in content) { 
    [node release]; 
} 

但我觉得我做错了什么......或者至少我不知道发生了什么事情的...请你能给我一点线索吗?

谢谢!

回答

6

copy创建为1的保留计数的对象,-addObject:增加了一个额外保留,所以你必须要么释放eventNode将其添加到阵列后或自动释放的副本:

[content addObject:[[eventNode copy] autorelease]]; 
2

您应该使用

CXMLNode *tempEventNode = [eventNode copy]; 
    [content addObject:tempEventNode]; 
    [tempEvent release]; 

代替,[content addObject:[eventNode copy]];

当您使用[eventNode copy]它使得r etaincount +1,当你直接添加这个副本(如在你的代码中),你将再次增加+1,因为数组会保留它。所以对于阵列保留它不是你的责任释放,但对于你的副本调用你必须释放它。

[eventNode copy] --> retain count +1 
[content addObject:[eventNode copy]]; -> retaincount +2 

感谢