關于UITableViewCell重用機制的理解

  • UITableViewCell的重用機制體現在-(UITableViewCell)dequeueReusableCellWithIdentifier:(NSString)identifier這個方法中,他的基本意思就是在創建cell的時候為每一個cell都綁定一個identifier的標識。當cell從我們的視覺范圍中消失的時候,這個綁定了cell的標識就會被放到緩存池中。當tableView需要新的cell的時候,直接先去緩存池中尋找有沒有攜帶identifier的cell,若有的話直接復用;沒有的話,才去創建新的cell,并綁定標識identifier。所以從理論上講,倘若一屏最多顯示的cell個數為n個,那么需要攜帶identifier表示的cell最少只需n+1個。
  • 當然在某些情況下,我們不需要復用cell,因為cell的復用在當cell的個數比較少的情況下,對于性能的提升幾乎沒有作用,反而有可能會造成數據的錯亂,這時候我們不想再使用cell的重用機制,這時候該怎么辦呢?可以利用以下幾種方式來解決:
       方法1 將獲得cell的方法從- (UITableViewCell*)dequeueReusableCellWithIdentifier:(NSString*)identifier 換為-(UITableViewCell *)cellForRowAtIndexPath:(NSIndexPath *)indexPath
    
    

重用機制調用的就是dequeueReusableCellWithIdentifier這個方法,方法的意思就是“出列可重用的cell”,因而只要將它換為cellForRowAtIndexPath(只從要更新的cell的那一行取出cell),就可以不使用重用機制,因而問題就可以得到解決,雖然可能會浪費一些空間。

示例代碼:

[plain]

  • (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
    {
    static NSString *CellIdentifier = @"Cell";
    // UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier]; //改為以下的方法
    UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath]; //根據indexPath準確地取出一行,而不是從cell重用隊列中取出
    if (cell == nil) {
    cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
    }
    //...其他代碼
    }

  • (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
    {
    static NSString *CellIdentifier = @"Cell";
    // UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier]; //改為以下的方法
    UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath]; //根據indexPath準確地取出一行,而不是從cell重用隊列中取出
    if (cell == nil) {
    cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
    }
    //...其他代碼
    }

方法2 通過為每個cell指定不同的重用標識符(reuseIdentifier)來解決。
重用機制是根據相同的標識符來重用cell的,標識符不同的cell不能彼此重用。于是我們將每個cell的標識符都設置為不同,就可以避免不同cell重用的問題了。

示例代碼:

[plain]

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

    NSString *CellIdentifier = [NSString stringWithFormat:@"Cell%d%d", [indexPath section], [indexPath row]];//以indexPath來唯一確定cell
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier]; //出列可重用的cell
    if (cell == nil) {
    cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
    }
    //...其他代碼
    }

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

    NSString *CellIdentifier = [NSString stringWithFormat:@"Cell%d%d", [indexPath section], [indexPath row]];//以indexPath來唯一確定cell
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier]; //出列可重用的cell
    if (cell == nil) {
    cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
    }
    //...其他代碼
    }

方法3 刪除重用cell的所有子視圖

這個方法是通過刪除重用的cell的所有子視圖,從而得到一個沒有特殊格式的cell,供其他cell重用。

示例代碼:

[plain]

  • (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
    {
    static NSString *CellIdentifier = @"Cell";
    UITableViewCell cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier]; //出列可重用的cell
    if (cell == nil) {
    cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
    }
    else
    {
    //刪除cell的所有子視圖
    while ([cell.contentView.subviews lastObject] != nil)
    {
    [(UIView
    )[cell.contentView.subviews lastObject] removeFromSuperview];
    }
    }
    //...其他代碼
    }

-  js中的邏輯與(&&)和邏輯或(||):  
  在js中寫出如下的答案 :
  var a = 2;
  var b = 3;
  var andflag = a && b ;
  var orflag = a || b;
  乍一看,這是一道邏輯或和邏輯與的運算題,然而在webostorm中運行一下才發現結果是,andflag  = 3,orflag = 2;
  具體的執行原理如下:

在運算過程中,首先js 會將 && 和|| 兩邊的值轉成Boolean 類型,然后再算值 ,&&運算如果返回true,  
則取后面的值,如果|| 返回true,則取前面的值 , 而其中數值轉換成boolean 的規則 是:
對象、非零整數、非空字符串返回true,
其它為false ;

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容