tableView性能优化

作者: 木子小静 | 来源:发表于2016-07-05 15:53 被阅读267次

cell的循环利用方式1

1.先根据cell的标识在缓存池中查找可循环利用的cell


    static NSString *ID = @"cell";
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:ID];
    

2.如果cell为nil

  if (cell == nil) {
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleValue1 reuseIdentifier:ID];
    }

3.覆盖数据

cell.textLabel.text = @"";

完整版

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *ID = @"cell";
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:ID];
    if (cell == nil) {
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleValue1 reuseIdentifier:ID];
    }
    cell.textLabel.text = @"";
    return cell;
}

cell的循环利用方式2-注册

1.定义一个全局变量

    static NSString *ID = @"cell";

2.注册某个标识对应的cell类型

    [self.tableview registerClass:[UITableViewCell class] forCellReuseIdentifier:ID];

3.在数据源方法中返回cell

    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:ID];

4.覆盖数据

    cell.textLabel.text = @"";

完整版


static NSString *ID = @"cell";

- (void)viewDidLoad {
    [super viewDidLoad];
    // Do any additional setup after loading the view, typically from a nib.


    self.tableview.dataSource = self;
    self.tableview.delegate = self;
    [self.tableview registerClass:[UITableViewCell class] forCellReuseIdentifier:@"cell"];
}

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{

    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:ID];
    cell.textLabel.text = @"";
    return cell;
}

自定义cell

  • 等高cell
    • stryboard自定义cell
      • 1.常见一个继承自UITableViewCell的子类,如MuziCell
      • 2.在storyboard中
        • 往cell里面增加需要用到的子控件
        • 设置cell的重用标识
        • 设置cell的class为自定义cell的名字,MuziCell
      • 3.在控制器中
        • 利用重用标识找到cell
        • 给cell传递模型数据
      • 4.在MuziCell中
        • 讲storyboard中的子控件连线到类扩展中
        • 需要提供一个模型属性,重写模型的set方法,在这个方法中设置模型数据到子控件上
    • xib自定义cell
    • 代码自定义cell
      • 1.在initWithFrame:方法中添加子控件
      • 2.在autoLayout里面设置子控件的frame
      • 3.重写模型的set方法
  • 非等高cell
    • 拿到内容的y值就可知道cell的高度
      • 1.在tableVIew的heightForRow方法里创建一个临时的cell,将数据传进cell里面,可获得其高度,并通过[cell layoutIfNeeded]对其强制布局,但是这么做并不推荐,因为临时创建的cell,浪费内存,整个cell就是打酱油的。。。
    • 2.先返回每一行的估计高度(随便返回一个大致的高度即可),那么就会先调用cellForRow方法创建cell,在调用heightForRow获取cell的真是高度,这样就是用到哪个cell就创建哪个cell(没有估计高度的话,就是一次性创建所有的cell),在cellForRow上面获得数据的高度,然后保存起来传给heightforrow方法里面并且需要在cellforrow里面强制更新布局[cell layoutIfNeeded];

方法一的代码


-(CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath)indexPath
{
      MuziCell *cell = [MuziCell cellWithTableView:tableView];
      cell.status = self.statues[indexPath.row];    // 将数据传进cell
      [cell layoutIfNeeded];
      return cell.height;
}

方法二的代码


- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{

    MuziCell *cell = [MuziCell cellWithTableView:tableView];
    cell.status = self.statues[indexPath.row];    // 将数据传进cell
    [cell layoutIfNeeded];
    self.heights[@(indexPath.row)]  = @(cell.height); // 字典里面是对象
    return cell;
}

// 返回估计高度,非常重要,调节cellforRow和heightForRow的调用方法
- (CGFloat)tableView:(UITableView *)tableView estimatedHeightForRowAtIndexPath:(NSIndexPath)indexPath
{
      return 200;
}

- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath)indexPath
{
    // 将上面的高度存起来,拿到这里使用      
    return [self.heights[@(indexPath.row)] doubleValue];
}

相关文章

网友评论

本文标题:tableView性能优化

本文链接:https://www.haomeiwen.com/subject/kinlrttx.html