cant return cell in cellForRowAtIndexPath

后端 未结 4 1676
北荒
北荒 2021-01-15 15:44

i\'m trying to return different cells in a tableView. Normally in this case i would return different cells and then return nil at the bottom, but in this case it gives me an

4条回答
  •  无人共我
    2021-01-15 15:44

    As indicated in a previous answer for a similar question, -tableView:cellForRowAtIndexPath: must return a UITableViewCell. So you can't return nil. However, I would also recommend to avoid returning the following codes at the end of -tableView:cellForRowAtIndexPath: when you use if else or switch statements inside it:

    //bad code design
    var cell: UITableViewCell!
    return cell
    

    or:

    //bad code design
    var cell: UITableViewCell = tableView.dequeueReusableCellWithIdentifier("Cell", forIndexPath: indexPath) as UITableViewCell
    return cell
    

    You can do better code than creating an UITableViewCell instance that is never called just in order to silent Xcode warnings!

    So what would be the solution?

    The key thing is to be sure that your last possible value for an if else statement is set in else (not in else if). In the same way, the key thing is to be sure that your last possible value for a switch statement is set in default: (not in case XXX:).

    Thus, your code should look like this:

    override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
        if indexPath.row == 0 {
            let cell: UITableViewCell = tableView.dequeueReusableCellWithIdentifier("CellZero", forIndexPath: indexPath) as UITableViewCell
            /* ... */
            return cell
        } else if indexPath.row == 1 {
            let cell: UITableViewCell = tableView.dequeueReusableCellWithIdentifier("CellOne", forIndexPath: indexPath) as CellOne
            /* ... */
            return cell
        } else { //set your last indexPath.row case in "else", not in "else if indexPath.row == 2"!!!
            switch segment {
            case 0:
                let cell = tableView.dequeueReusableCellWithIdentifier("CellTwo", forIndexPath: indexPath) as CellTwo
                /* ... */
                return cell
            case 1:
                let cell = tableView.dequeueReusableCellWithIdentifier("CellThree", forIndexPath: indexPath) as CellThree
                /* ... */
                return cell
            default: //set your last segment case in "default:", not in "case 2:"!!!
                let cell = tableView.dequeueReusableCellWithIdentifier("CellFour", forIndexPath: indexPath) as CellFour
                /* ... */
                return cell
            }
        }
        //No need for a fictive "return cell" with this code!!!
    }
    

    If segment is not an optional, thanks to tuples, you can even reduce the previous code to this:

    override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
        switch (indexPath.row, segment) {
        case (0, _):
            let cell = tableView.dequeueReusableCellWithIdentifier("CellZero", forIndexPath: indexPath) as UITableViewCell
            /* ... */
            return cell
        case (1, _):
            let cell = tableView.dequeueReusableCellWithIdentifier("CellOne", forIndexPath: indexPath) as CellOne
            /* ... */
            return cell
        case (2, 0):
            let cell = tableView.dequeueReusableCellWithIdentifier("CellTwo", forIndexPath: indexPath) as CellTwo
            /* ... */
            return cell
        case (2, 1):
            let cell = tableView.dequeueReusableCellWithIdentifier("CellThree", forIndexPath: indexPath) as CellThree
            /* ... */
            return cell
        default: //case (2, 2)
            let cell = tableView.dequeueReusableCellWithIdentifier("CellFour", forIndexPath: indexPath) as CellFour
            /* ... */
            return cell
        }
    }
    

提交回复
热议问题