2014-04-20 34 views
1

是不是很好的做法,以释放任何项目内使用后创建的方法或类内?Objective-C应该在使用后将数组设置为零吗?

举例来说,如果我有这样的方法:

-(NSArray *)splitClassesWithData:(NSData *)data { 
    NSString *htmlString = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding]; 

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

    NSUInteger length = [htmlString length]; 
    NSRange range = NSMakeRange(0, length); 
    while(range.location != NSNotFound) 
    { 
     range = [htmlString rangeOfString: @"lblperiod" options:0 range:range]; 
     if(range.location != NSNotFound) 
     { 
      range = NSMakeRange(range.location + range.length, length - (range.location + range.length)); 
      NSNumber *toAdd = [NSNumber numberWithInteger:range.location]; 
      [classes addObject:toAdd]; 
     } 
    } 

    int counter = 0; 
    NSNumber *count = [NSNumber numberWithInteger:[classes count] - 1]; 
    NSMutableArray *classArray = [NSMutableArray arrayWithCapacity:[classes count]]; 

    for (NSNumber *i in classes) { 
     int loc = [[classes objectAtIndex:counter] intValue]; 
     int len = -loc; 

     if ([count intValue] > [[NSNumber numberWithInt:(counter)] intValue]) { 
      NSRange range = NSMakeRange(loc, (len + [[classes objectAtIndex:(counter+1)] intValue])); 
      NSString *rangeString = [htmlString substringWithRange:range]; 

      if ([rangeString rangeOfString:@"Academic Adviso"].location == NSNotFound) { 
       [classArray addObject:htmlString]; 
      } else { 
       NSLog(@"disinclude AA"); 
      } 

     } else { 
      NSRange range = NSMakeRange(loc, ([htmlString length] + len)); 
      htmlString = [htmlString substringWithRange:range]; 

      [classArray addObject:htmlString]; 
     } 
     counter++; 
    } 
    return [classArray copy]; 
} 

我应该设置classes为零?它会释放它吗?它是否自动发生?

+0

如果你使用ARC,那么你不需要这样做。它由编译器为您完成。 – Fogmeister

+0

在ARC本地创建的对象超出范围时被销毁。如果你要在一个循环内创建大量的NSSArray或NSDictionary,并将它们的副本添加到另一个对象,那么你应该将nil设置为NSArray或NSDictionary,以便ARC可以释放它。 –

回答

1

要认识到的一点是,当你设置对象为nil,你只是设置一块内存为对象,以零设置,这仅仅是一个比特集 - 像什么其他。所以,设置对象nil不会导致对象被释放。当一个对象不再有任何引用或者即将离开作用域时,应该从内存中释放对象 - 例如,它定义的方法已经完成并返回。

您可以通过调用其释放方法来释放对象。这意味着下一次系统出现时它会看到对象已经释放并且清除了内存(简单来说......) 另一种选择是在对象上调用autorelease。当你没有完成对象的情况下,这是非常有用的,但是不知道什么时候你会完成,并且不知道对象将在哪里结束 - 例如,表示对象的一段数据的对象服务器可能会从控制器传递到控制器并查看。使用autorelease确保在某些时候内存将被释放。你可以看到,它跟踪每个对象的状态变得非常棘手,所以一直沿着ARC(自动引用计数)。基本上它会为你考虑这一切,假设它已启用。

就你而言,如果你有ARC,那么你的代码在内存管理方面是最好的。如果不是的话,那么有很多东西需要像autoreleasing你返回的数组副本那样处理。我建议你看一下这个文档,以获得对iOS环境中内存管理的更多理解 - 从运行时你会得到令人困惑的基于内存的错误的长期运行,它将帮助你。

https://developer.apple.com/library/mac/documentation/Cocoa/Conceptual/MemoryMgmt/Articles/MemoryMgmt.html

希望它能帮助。

0

如果你正在使用ARC(而且我非常确定你是),那么就没有必要清零了。它将超出范围,将不会引用阵列,并且其内存将被释放。

0

如果使用Automatic Reference Counting那么代码是正确的,编译器会自动插入retain/release/autorelease调用。
但是你没有使用ARC,那么你应该手动进行。你的情况:

- (NSArray *)splitClassesWithData:(NSData *)data { 
    // ... 
    // Main method logic 
    // ... 
    [classes release]; 
    return [[classArray copy] autorelease]; 
相关问题