UITableView numberOfRowsInSection崩溃:segue跳转时magazinesIndex为nil
解决Segue跳转时Nil值崩溃的问题
你的问题根源在于手动创建的控制器实例和Segue实际跳转的控制器实例完全是两个不同的对象,导致你设置的参数根本没传递到真正要显示的控制器里,最终magazinesIndex为nil引发崩溃。下面是具体的修复方案:
问题分析
你在didSelectRowAt里手动初始化了MagazineTableViewController并调用customInit,但performSegue(withIdentifier:)会从Storyboard中重新创建一个目标控制器实例——这两个实例毫无关联,所以真正跳转过去的控制器里magazinesIndex还是初始的nil值,当numberOfRowsInSection尝试访问MagazinesData[magazinesIndex]时就会崩溃。
正确的修复步骤
1. 修改TableViewController1的代码,使用Segue的prepare(for:sender:)方法传递数据
这是iOS中Segue跳转传递数据的标准方式,不要手动创建控制器实例。修改后的代码如下:
override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) { // 把indexPath作为sender传递,方便在prepare方法中获取数据 self.performSegue(withIdentifier: "company", sender: indexPath) tableView.deselectRow(at: indexPath, animated: true) } // 新增Segue准备方法,用于传递数据 override func prepare(for segue: UIStoryboardSegue, sender: Any?) { // 先判断Segue标识符是否匹配 guard segue.identifier == "company" else { return } // 把目标控制器转为MagazineTableViewController类型 guard let destinationVC = segue.destination as? MagazineTableViewController else { print("无法转换为MagazineTableViewController") return } // 从sender中取出之前传递的indexPath guard let indexPath = sender as? IndexPath else { return } // 直接给目标控制器的属性赋值 destinationVC.magazinesIndex = indexPath.row destinationVC.title = topics[indexPath.row] }
2. 简化TableViewController2的代码
去掉不需要的customInit方法,确保属性可以被外部赋值:
let MagazinesData = [//an array containing arrays of magazines] // 建议设置为非可选类型,因为我们会确保在跳转前赋值 var magazinesIndex: Int = 0 override func viewDidLoad() { super.viewDidLoad() } override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int { return MagazinesData[magazinesIndex].count } override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell { let cell = tableView.dequeueReusableCell(withIdentifier: "cell", for: indexPath) as! MagazineTableViewCell cell.magazineTitle?.text = MagazinesData[magazinesIndex][indexPath.row] return cell }
额外注意事项
- 确保Storyboard中Segue的标识符
"company"和代码中的完全一致 - 确认两个TableViewController在Storyboard中都正确设置了对应的类
- 如果
topics数组可能为空,建议在didSelectRowAt中先做非空判断,避免越界访问
内容的提问来源于stack exchange,提问作者user9137935
相关产品推荐
相关产品推荐

