zoukankan      html  css  js  c++  java
  • 用xib自定义UITableViewCell的注意事项——重用

    问题的提出:

    有时候我们经常需要自定义tableView的cell,当cell里面的布局较为复杂时往往舍弃纯代码的方式而改用xib的方式进行自定义。当我们用纯代码的方式布局cell时,往往会在cell的initWithStyle: reuseIdentifier: 方法里面用纯代码进行布局,然后在外部VC的cellForRowAtIndexPath方法里面我们会这么写,假定自定义的cell为Cell,继承自UITableViewCell:

    static NSString *CellIdentifier = @"Cell";
        Cell *cell = (Cell *)[tableView dequeueReusableCellWithIdentifier:CellIdentifier];
        if (!cell) {
            cell = [[[Cell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease];
        }
        cell.titleLabel.text = [self.dataList objectAtIndex:indexPath.row];
        return cell;

    上述这么写完全没有问题,因为教科书跟各种教程都是这么写的,上述代码对cell进行了重用。但如果我们现在想用xib来布局呢?看到过不少代码是这么写的:

    static NSString *CellIdentifier = @"Cell";
        Cell *cell = (Cell *)[tableView dequeueReusableCellWithIdentifier:CellIdentifier];
        if (!cell) {
            
            cell = [[[NSBundle mainBundle] loadNibNamed:NSStringFromClass([Cell class])
                                                 owner:self
                                               options:nil] objectAtIndex:0];
            //cell = [[[Cell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease];
        }
        cell.titleLabel.text = [self.dataList objectAtIndex:indexPath.row];return cell;

    唯一区别的地方在于红色的位置:cell的初始化不再通过initWithStyle函数,因为我们现在用xib布局,所有的控件信息都在xib里面,因此我们根据Cell所对应的xib名称来加载xib以创建cell。但是你注意到没,第二种方法的红色部分并没有包含任何重用信息,也就是说,每次拖动tableview,都会一直创建不同的cell,当要显示的cell很多时内存问题就显露出来了。

    为了解决这个问题,我们换用另一种更好的方式。

    直接放优化后的代码,UINib类可以先不看,不影响代码的理解:

    static NSString *CellIdentifier = @"Cell";
        BOOL nibsRegistered = NO;
        if (!nibsRegistered) {
            UINib *nib = [UINib nibWithNibName:NSStringFromClass([Cell class]) bundle:nil];
            [tableView registerNib:nib forCellReuseIdentifier:CellIdentifier];
            nibsRegistered = YES;
        }
        Cell *cell = (Cell *)[tableView dequeueReusableCellWithIdentifier:CellIdentifier];
        cell.titleLabel.text = [self.dataList objectAtIndex:indexPath.row];
        return cell;

    我们可以看到,红色部分很好地满足了我们的需求:既从nib加载,又能对cell进行重用。下面对代码进行解释:

    1.UINib是一个IOS4.0才出现的类,与MAC上的NSNib类作用相似, 就是加速频繁使用的NIB文件的加载。在第一次从硬盘加载NIB时,它在内存中缓存NIB文件对象。之后加载NIB文件时就会从内存拷贝而避免了较慢的硬盘访问。Apple宣称可以在 加载NIB文件时提供 2倍的速度提升 。 使用UINib的最明显的地方就是在需要在每次创建新Cell时从NIB文件中加载Cell的UITableViewControllers中。UINib的优势就是在不用大量修改代码的情况获得性能改进。其实简单地说,就是利用缓存机制避免了频繁从硬盘中加载XIB文件,这在大数据量的时候显得尤为有用。

    2.除了上述代码,还需要在xib文件中做如下设置:在Cell.xib的Inspector窗口中将Identifier进行设置,这里的Identifier要与cellForRowAtIndexPath中一致。

    以上就是从xib加载自定义UITableViewCell的注意事项以及解决方案,很多人采用了第二种方法,看起来虽然没问题但是一旦内存吃紧的时候问题就暴露出来了!

  • 相关阅读:
    手把手教你在Android手机上实现蓝牙键盘的支持
    python 字符编码
    vi常用命令
    EditPlus for python
    Eclipse安装pydev插件
    手把手教你在Android手机上实现蓝牙键盘的支持
    2020年7月23日
    2020年7月20日
    2020年7月18日
    2020年7月22日
  • 原文地址:https://www.cnblogs.com/sanjianghuiliu/p/4070904.html
Copyright © 2011-2022 走看看