我应该什么时候释放我的数组



我正在解析来自互联网的一些JSON,然后将它们添加到一个数组中,该数组是我的UITableView的数据源。我不确定什么时候该释放我的阵法?

.h:项目

@property(nonatomic,retain)NSMutableArray*  items;

.m:connectionDidFinishLoading

// fetch succeeded    
    NSString* json_string = [[NSString alloc] initWithData:retrievedData encoding:NSUTF8StringEncoding];
    //Check ST status
    int status =  [[[[json_string objectFromJSONString] valueForKey:@"response"] valueForKey:@"status"]intValue];
    //NSLog(@"Status: %d", status);
    items = [[NSMutableArray alloc] init];
    NSDictionary* messages = [[NSDictionary alloc] init]; 
    switch (status) {
        case 200:
            messages = [[[json_string objectFromJSONString] valueForKey:@"messages"] valueForKey:@"message"];
            for (NSDictionary *message in messages)
            {
                [items addObject:message];
            }
            [self.tableView reloadData];
        break;
        default:
        break;
    }

首先,如果您打算在items上调用addObject:,则可能需要将其声明为NSMutableArray的实例。

第二,将其声明为属性,这样,如果你最终多次获得它,旧的值将在你这样做时释放。

self.items = [NSMutableArray array];

而释放它的正确点应该是dealloc

如果您:,您可能不想立即发布它

  • 对详细信息视图使用didSelectRowAtIndexPath:方法,并将此数据传递给它们
  • 在cellForRowAtIndexPath:方法中定义自定义UITableViewCell样式
  • 在其他地方使用此数据

最佳实践是声明一个实例变量并在.m中对其进行合成,在适当的操作中使用,并在dealloc方法中释放。

您可以使用的一个可能的发布点是刷新表中显示的数据。

示例:

我从应用程序中的API获取数组中的字典,并使用类似的东西。

MyTableViewController.h

@interface MyTableViewController {
    NSMutableArray *items;
}
@property (nonatomic, retain) NSMutableArray *items;
@end

MyTableViewController.m

@implementation MyTableViewController
@synthesize items;
- (void)dealloc
{
    [items release];
    [super dealloc];
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
    return [items count];
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
    static NSString *cellIdentifier = @"FilesCellIdentifier";
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier];
    if (cell == nil) {
        cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:cellIdentifier] autorelease];
    }
    cell.textLabel.text = [[items objectAtIndex:indexPath.row] valueForKey:@"name"];
    cell.imageView.image = [UIImage imageNamed:[[NSString alloc] initWithFormat:@"filetype_%@.png", [[items objectAtIndex:indexPath.row] valueForKey:@"type"]]];
    return cell;
}
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
        MyDetailViewController *detailViewController = [[MyDetailViewController alloc] initWithNibName:@"MyDetailViewController" bundle:[NSBundle mainBundle]];
        detailViewController.item = [items objectAtIndex:indexPath.row];
        [self.navigationController pushViewController:detailViewController animated:YES];
        [detailViewController release];
        detailViewController = nil;
    }
}
- (void)getItems
{
    [items release];
    items = [[NSMutableArray alloc] init];
    //Do some requests here
    for (NSDictionary *dict in results)
    {
        [items insertObject:dict atIndex:0];
    }
    [self.tableView reloadData];
    [self stopLoading];
}
@end

在错误的位置释放一段时间会导致内存泄漏,在分配之前,u可以有一个类似于if()的条件{[…release]}。未经测试,但这种释放可以避免泄漏。

最常见的是将items变量作为类的属性,一旦您可能需要在tableView:cellForRowAtIndexPath:方法中使用它。

因此,将其作为属性变量,可以在dealloc方法上释放它。

很明显,UITableView将使用您的数组item来显示数据。

首先在.h类中将其声明为实例变量。

.h类

@interface MyClass 
{
  MSMutableArray* items;
}
@property(nonatomic,retain) MSMutableArray* items;
@end

.m类中。

@synthesis iMyArray;

并且你填充数组的代码应该是

NSMutabelArray* itemsTemp = [[NSMutabelArray alloc] initWithCapacity:1];
messages = [[[json_string objectFromJSONString] valueForKey:@"messages"] valueForKey:@"message"];
[json_string release];
for (NSDictionary *message in messages) {
    NSLog(@"%@",[message valueForKey:@"body"]);
    [itemsTemp addObject:message];
}

self.items= itemsTemp;
[itemsTemp release];
itemsTemp = nil;
[self.tableView reloadData];

现在在dealloc中发布您的数组实例。

-(void) dealloc
{
   if(items )
   {
    [items release];
    items = nil ;
   }
   [super dealloc];
}

正确的方法是在.h类中使其成为属性,因为您已经将其声明为属性:记住,有一件事总是使用self来分配属性。

您的声明items=[[NSMutableArray alloc] init];

是错误的。(使用self)也因为您的属性是retain类型,所以对其使用alloc会增加保留计数。这会给您带来泄漏。

因此在viewDidLoad 中以这种方式使用

NSMutableArray *tempArray=[[NSMutableArray alloc] init];
self.items=tempArray;
[tempArray release];

然后在dealloc中释放你的物品数组,并在viewDidUnload 中将其设置为零

- (void)viewDidUnload {
    [super viewDidUnload];
    self.items=nil;
}
- (void)dealloc {
    [self.items release];
[super dealloc];
}

希望现在你能明白你应该如何使用这个。

根据苹果的UITableView重载数据方法文档:

"[…]为了提高效率,表视图只重新显示那些可见的行"

这意味着只要表正在使用,yo就不应该释放items数组,即必须将数组声明为属性。

首先,因为如果滚动视图,仍然需要items信息来显示下面或上面的行。

第二,因为作为一个属性,如果您碰巧为items分配了一个新值,您可以确保以前的值将被释放。

最后,发布属性的常见位置是在dealloc方法中,具体取决于您在viewDidUnload方法中的实现。

最新更新