我有一个非常复杂的表视图设置,我决定使用块结构来创建和选择单元格,以简化未来的开发和更改.
我正在使用的结构如下所示:
var dataSource: [( cells:[ (type: DetailSection, createCell: ((indexPath: NSIndexPath) -> UITableViewCell), selectCell: ((indexPath: NSIndexPath) -> ())?, value: Value?)], sectionHeader: (Int -> UITableViewHeaderFooterView)?, sectionFooter: (Int -> UITableViewHeaderFooterView)? )] = []
然后我可以在setup函数中设置表格,并使我的委托方法相当简单
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell { let cell = dataSource[indexPath.section].cells[indexPath.row].createCell(indexPath:indexPath) return cell } func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int { return dataSource[section].cells.count } func numberOfSectionsInTableView(tableView: UITableView) -> Int { return dataSource.count }
我之前在另一个TVC做过类似的设置
var otherVCDataSource: [[ (type: DetailSection, createCell: ((indexPath: NSIndexPath) -> UITableViewCell), selectCell: ((indexPath: NSIndexPath) -> ())?)]] = []
这个解决方案效果很好.
当我尝试访问其中一个createCell块中的indexPath时,带有sectionHead和footer的当前dataSource会给我一个EXC_BAD_ACCESS.
createCell: { (indexPath) in let cell:CompactExerciseCell = self.tableView.dequeueReusableCellWithIdentifier(self.compactExerciseCellName, forIndexPath:indexPath) as! CompactExerciseCell cell.nameLabel.text = "\(indexPath.row)" cell.layoutMargins = UIEdgeInsetsZero return cell }
该应用程序总是崩溃
self.tableView.dequeueReusableCellWithIdentifier(self.compactExerciseCellName, forIndexPath:indexPath)
我在这里错过了什么?为什么我不能在旧结构中正常工作时访问新结构中的indexPath?这个元组和数组之间的内存管理有什么不同?
更新:所以我有一个截止日期,最后我不得不放弃并重新编写数据结构.
我的第一次尝试是不是将indexPath作为参数发送,而是发送行和节并在块内重建indexPath.这适用于数据结构内部的所有内容但如果我在单元格上单击另一个视图控制器,则在下一个VC中出现单元格时,我得到另一个非常奇怪的崩溃(一些malloc错误,这在我使用ARC时很奇怪).
我试图在这次崩溃中四处寻找,但没有时间花在这上面所以我不得不转向另一个解决方案.
而不是这个元组数组[([] ,,)]我做了两个数组; 一个用于单元格,一个用于页眉和页脚.这个结构消除了indexPath崩溃的问题,但是我仍然遇到了下一个VC中的问题,它在出列单元格时没有停止崩溃.
最终解决方案或解决方法是使用此扩展名"安全地"访问单元格创建者和选择器:
extension Array { subscript (safe index: Int) -> Element? { return indices ~= index ? self[index] : nil } }
基本上tableView委托函数中的return语句如下所示:
return dataSource[safe:indexPath.section]?[safe:indexPath.row]?.createCell?(indexPath: indexPath)
代替
return dataSource[indexPath.section][indexPath.row].createCell?(indexPath: indexPath)
我无法看到它如何对下一个VC 产生任何影响,因为如果在数据结构中执行nil或查找非现有索引存在问题,则单元格甚至不应该存在,但这仍然解决了我遇到的问题在下一个VC中出列的单元格.
我仍然不知道为什么数据结构的变化和从数组获取值的安全扩展有帮助,如果有人有任何想法我会很高兴听到它但我现在不能在解决方案中进行更多实验.我的猜测是值的安全访问以某种方式重新分配了值并阻止它们被释放.也许元组让编译器无法理解值应该保存在内存中,或者我的代码中只有一个幽灵.我希望有一天我可以回过头来仔细研究一下......