ios - 在获取数据期间索引超出部分中的行数范围
问题描述
何时尝试使用我的表格视图和进度条打开新控制器时出现“索引超出范围”。我从 Firestore 数据库中获取数据,想法是当我点击“下一步”按钮时,我想更新进度条并使用新值重新加载表视图。行数必须等于组数,但每个练习都有不同的组数,所以我想动态更改行数。
class StartViewController: UIViewController, UITableViewDelegate, UITableViewDataSource {
var titleValue: String = ""
var dayOfWorkout: String = ""
var exerciseNumber = 0
var models: [DataCell2] = []
let user = Auth.auth().currentUser
var db = Firestore.firestore()
@IBOutlet weak var tableView: UITableView!
@IBOutlet weak var exerciseLabel: UILabel!
@IBOutlet weak var progressView: UIProgressView!
override func viewDidLoad() {
super.viewDidLoad()
progressView.transform = progressView.transform.scaledBy(x: 1, y: 3)
tableView.delegate = self
tableView.dataSource = self
retrieveWorkouts()
}
@IBAction func nextButtonPressed(_ sender: UIButton) {
nextExercise()
Timer.scheduledTimer(timeInterval: 0.2, target: self, selector: #selector(updateUI), userInfo: nil, repeats: false)
tableView.reloadData()
}
@objc func updateUI() {
progressView.progress = getProgress()
}
func getProgress() -> Float {
return Float(exerciseNumber) / Float(models.count)
}
func nextExercise() {
if exerciseNumber + 1 < models.count {
exerciseNumber += 1
} else {
exerciseNumber = 0
}
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
**//HERE IS ERROR**
return models[exerciseNumber].sets!
}
以及从 Firestore 获取数据的方法
func retrieveWorkouts() {
db.collection("users").document("\(user!.uid)").collection("WorkoutsName").document("\(titleValue)").collection("Exercises").order(by: "Number").getDocuments { (querySnapshot, error) in
if let error = error{
print("\(error.localizedDescription)")
}else {
if let snapshotDocuments = querySnapshot?.documents {
for doc in snapshotDocuments {
let data = doc.data()
if let numberDb = data["Number"] as? Int, let exerciseDb = data["Exercise"] as? String, let kgDb = data["kg"] as? Int, let setsDb = data["Sets"] as? Int, let repsDb = data["Reps"] as? Int, let workoutName = data["workoutName"] as? String {
print("data is \(data)")
let newModel = DataCell2(Number: numberDb, Exercise: exerciseDb, kg: kgDb, sets: setsDb, reps: repsDb, workoutName: workoutName)
self.models.append(newModel)
self.tableView.reloadData()
}
}
}
}
}
}
解决方案
您基于的行数
models[exerciseNumber].sets!
并且您正在将锻炼次数设置为
func nextExercise() {
if exerciseNumber + 1 < models.count {
exerciseNumber += 1
} else {
exerciseNumber = 0
}
}
但是,您在这里有一个逻辑错误:您正在检查练习数是否小于 models.count,如果是,则增加它。这将导致exerciseNumber == models.count,并且由于数组是零索引的,这将超出数组的末尾并给出超出范围的错误。
一个简单的解决方法是将方法更改为:
func nextExercise() {
exerciseNumber += 1
if exerciseNumber == models.count {
exerciseNumber = 0
}
return exerciseNumber
}
有更聪明的方法可以做到这一点,但现在这将起作用。
推荐阅读
- django - 循环输入字段名称
- c# - 使用可变变量从 Json url 获取值
- generics - 从可转换为多种类型的函数返回值
- javascript - 将元素添加到现有的 React DropdownButton
- android - 为什么离子按钮和离子徽章垂直未对齐
- x86-64 - 使用 iced_x86 反汇编时如何处理 exe 的标头?
- powershell - 为什么我的 elseif 块在指定 -WhatIf 时运行
- java - 如何更改已在 Play 商店发布的应用的签名密钥?contentProvider 还有另一种有效的替代方案吗?
- discord - 无法编译:模块 Discord 未定义 Discord 类型
- javascript - 如果对象值改变,数组值改变