我用Swift制作了一个TableView,在其中显示了UiTextField中填充的查询的搜索结果。
let cellReuseIdentifier = "cell"
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cell:SearchCell = self.tableView.dequeueReusableCell(withIdentifier:cellReuseIdentifier) as! SearchCell
cell.objectName.text = self.search_results_list[indexPath.section]
return cell
}
在值更改事件中,我触发了搜索操作:
@IBAction func searchInputChanged(_ sender: Any) {
self.search_results_list = []
let search = self.searchField.text
let parameters: Parameters = ["api_token": token, "search": search!+" "]
let URL = "https://myweb.app/api/search"
Alamofire.request(URL, parameters: parameters).responseArray { (response: DataResponse<[SearchResponse]>) in
let searchResultsArray = response.result.value
if let searchResultsArray = searchResultsArray {
for searchResult in searchResultsArray {
self.search_results_list.append(searchResult.description!)
}
}
// Then I reloeadData of the TableView
self.tableView.reloadData()
}
}
还有NumberOfSections方法:
func numberOfSections(in tableView: UITableView) -> Int {
return self.search_results_list.count
}
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return 1
}
它确实可以工作,但是当我快速填写表格时,Array具有正确的顺序,但是TableView具有不同的顺序。当我检查数组时,我看到顺序是正确的,但是TableView显示了一个不同的顺序。当我等待一秒钟并在末尾添加一个空格时,TableView确实显示了正确的顺序。 当我逐个字母添加字母并在每个字母重新加载tableview之后等待时,输出是正确的
我想念什么?
答案 0 :(得分:1)
就像他们在评论中说的那样。可能是因为异步调用在不同的时间返回。与结果结果较少(较新的电话)的人相比,结果更多结果(较早的电话)的人可能会更快。因此,您要做的是使与您的当前搜索文本不匹配不匹配的每个API响应无效。
@IBAction func searchInputChanged(_ sender: Any) {
self.search_results_list = []
let search = self.searchField.text
let parameters: Parameters = ["api_token": token, "search": search!+" "]
let URL = "https://myweb.app/api/search"
Alamofire.request(URL, parameters: parameters).responseArray { (response: DataResponse<[SearchResponse]>) in
if search == self.searchTextField.text { // Compare search text with current text in searchTextField.
let searchResultsArray = response.result.value
if let searchResultsArray = searchResultsArray {
for searchResult in searchResultsArray {
self.search_results_list.append(searchResult.description!)
}
}
DispatchQueue.main.async {
self.tableView.reloadData()
}
}
}
}
重要的优化提示
您可以将API调用包装在计时器中,以便仅在用户停止在文本字段中输入字符时才单击。这有助于避免不必要的API调用。您可以通过使用Timer
进行网络调用来实现。在textDidChange
中启动计时器,如果在短时间内(0.5s或您认为最佳的状态)再次调用该委托,则使该计时器无效。