You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Swift开发购物App时UITableView cell赋值出现Index out of range错误

Swift购物App UITableView索引越界问题解决方案

核心问题原因

触发Index out of range的本质是UITableView要求渲染的行数,大于对应数据源数组的元素个数,从给出的代码来看,有三个直接触发问题的原因:

  1. numberOfRowsInSection方法返回值和数据源数组长度不匹配:如果该方法返回了固定数值、或者返回了长度更大的其他数组的count,就会出现tableView要渲染第N行,但namee/myprice/mySecond数组没有第N个元素的情况。
  2. 多数据源数组不同步:解析逻辑只更新了namee、myprice、myphoto三个数组,但cell赋值时用到了mySecond数组,若没有在解析时同步更新mySecond数组的元素,就会出现数组长度不一致,访问越界。
  3. 强制解包、同步加载网络图片的隐性风险:代码中大量使用!强制解包、try!执行抛出方法,一旦数据不符合预期就会直接崩溃,同步加载网络图片还会卡住主线程影响交互。

修复步骤

步骤1:修正行数返回逻辑

确保numberOfRowsInSection返回值和用来做渲染的数据源数组长度完全一致:

override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    // 如果继续用多个独立数组,返回所有数组中长度最小的值,优先建议替换为单数据源数组
    return namee.count
}

步骤2:修复数据源同步问题

统一替换为单数据源数组,避免多数组不同步的问题:
首先定义统一的商品模型:

struct GoodsModel: Codable {
    let name: String
    let price: String
    let imageUrl: URL
}
// 全局只维护一个数据源数组
var goodsList: [GoodsModel] = []

调整解析逻辑:

func extracted(){
    guard let url = URL(string: "http://rajeshrmohan.com/sport.json") else {
        return
    }
    let task = URLSession.shared.dataTask(with: url){ (data,response,error) in
        guard let dataResponse = data, error == nil else {
            print(error?.localizedDescription ?? "Response Error")
            return
        }
        do {
            let decoder = JSONDecoder()
            let model = try decoder.decode(FullClothes.self, from: dataResponse)
            // 清空原有数据避免重复添加
            self.goodsList.removeAll()
            for item in model.item {
                // 可选绑定过滤无效数据,避免崩溃
                guard let name = item.name, let price = item.price, let imageStr = item.image, let imageUrl = URL(string: imageStr) else {
                    continue
                }
                self.goodsList.append(GoodsModel(name: name, price: String(price), imageUrl: imageUrl))
            }
            DispatchQueue.main.async {
                self.tableView.reloadData()
            }
        } catch let parsingError {
            print("Error", parsingError)
        }
    }
    task.resume()
}

步骤3:优化cell赋值逻辑

移除强制解包,改用异步加载图片,增加数组越界防护:

override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCell(withIdentifier: "hello", for: indexPath) as! DisplayShopTableCellTableViewCell
    // 越界防护
    guard indexPath.row < goodsList.count else {
        return cell
    }
    let goods = goodsList[indexPath.row]
    cell.userLbl.text = goods.name
    cell.passLbl.text = goods.price
    // 异步加载图片,避免卡主线程和强制崩溃
    DispatchQueue.global().async {
        if let imageData = try? Data(contentsOf: goods.imageUrl), let image = UIImage(data: imageData) {
            DispatchQueue.main.async {
                // 防止cell复用出现图片错乱
                if tableView.indexPath(for: cell) == indexPath {
                    cell.tablecellimageview.image = image
                }
            }
        }
    }
    return cell
}

内容的提问来源于stack exchange,提问作者KAKEN

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.26 10:45:04