【问题标题】:Using dequeueReusableCellWithIdentifier does not appear faster (or lower memory)?使用 dequeueReusableCellWithIdentifier 不会显得更快(或更低的内存)?
【发布时间】:2014-02-28 18:08:09
【问题描述】:

当我想创建一个包含自定义单元格的表格时,这就是我编写标准代码的方式:

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *cellIdentifier = @"CustomCell";
    CustomCell *cell = (CustomCell*)[tableView dequeueReusableCellWithIdentifier:cellIdentifier];

    if (cell == nil)
    {
        NSArray *topLevelObjects = [[NSBundle mainBundle] loadNibNamed:@"CustomCell" owner:self options:nil];
        cell = [topLevelObjects objectAtIndex:0];
        cell.selectionStyle = UITableViewCellSelectionStyleNone;
    }
    else
    {
        NSLog(@"reuse!");
    }

    cell.property1 = ....
    cell.property2 = ....
    return cell;
} 

这就是我创建自定义单元格的大致方式:

  • 创建一个CustomCell.h(继承UITableViewCell)和CustomCell.m和一个CustomCell.xib
  • 在CustomCell.xib中,将顶层UIView的'class'属性改为'CustomClass'

我已经这样做了一段时间,但今天我终于决定做一个测试,看看表格是否真的正确地重用了单元格。

不。该表没有重复使用任何单元格!。上面代码 sn -p 中的 NSLog(@"reuse!") 永远不会被触发。

我决定使用以下两种方法对一个包含 100 万个单元格的 tableview 进行性能比较:

方法#1使用了上述方法。请注意,UIView 是我的 CustomCell.xib 中的顶级视图,并且在 xib 上没有配置重用标识符

  • 单元格未重用(NSLog 已重用!未打印)
  • 内存峰值约 3.4MB,CPU 峰值 60%
  • 滚动流畅

方法#2在xib的顶层使用了一个UITableViewCell,我把我所有的控件都放在了这个UITableViewCell的内容视图上。在 XIB 中,我将此单元格的重用标识符配置为“CustomCell”。

  • cell 重复使用(NSLog 重复打印多次)
  • 内存峰值约 6.1MB,CPU 峰值约 88%
  • 滚动流畅

两个问题:

  1. 为什么我没有看到方法 #2 的 CPU 和内存使用率低得多,方法 #1 是错误的,方法 #2 是正确的,因为方法 #1 根本没有重用任何单元格吗?或者换个角度看,为什么方法 #1 一次又一次愚蠢地加载 nib 仍然滚动得这么好?

  2. 为自定义单元格创建自定义 xib 时,顶层对象是 UIView 还是 UITableViewCell 有什么区别? (看起来没什么区别?)

【问题讨论】:

  • 你的单元格有多大和复杂,有多少子视图,有多少图像/图标/阴影/渐变?

标签: ios objective-c cocoa-touch uitableview


【解决方案1】:

您的 XIB 文件中似乎没有正确设置 reuseIdentifier

您也可以通过添加以编程方式设置它

[yourTable registerNib:[UINib nibWithNibName:@"CustomCell" bundle:nil] forCellReuseIdentifier:@"CustomCell"];

在使用表格视图之前的某个地方。以viewDidLoad 为例。

更新

问题1.如果不设置cell复用标识符,cell生命周期如下:

1.它被创建了。

2.显示出来了。

3.移出可见区域。

4.不再需要所以删除了。

如果您使用重用标识符单元格,典型的生命周期是:

1.从可重用队列中弹出..

2.显示出来了。

3.移出可见区域。

4.被推送到可重用队列。

所以性能差异是由于执行速度更快:创建/释放操作或弹出/推送。两种变体的内存使用量应该大致相同。

【讨论】:

    【解决方案2】:

    你需要实现

    -(NSString *)reuseIdentifier {
    
    return @"CustomCell";
    
    } 
    

    在你的单元格类CustomCell中,因为reuseIdentifier只读属性,你不能从外部设置它

    【讨论】:

    • 哦,你是对的......我刚刚测试它确实是一个只读属性。
    • 你有时间看看我的问题1和2吗?我很困惑。嗯。
    • 关于问题#2 UITableViewCell 只是 UIView 的子类,所以如果我理解正确的话没有区别。
    • 好的,我想我现在明白了。事实上,一旦我按照您的建议添加了reuseIdentifier 方法,我的代码现在就可以正确重用了!即使我的顶层是 UIView 而不是 UITableViewCell。
    猜你喜欢
    • 2012-01-28
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-03-12
    • 1970-01-01
    • 2023-03-15
    • 1970-01-01
    • 2014-01-16
    相关资源
    最近更新 更多