#swift #closures
#swift #замыкания
Вопрос:
Я создал замыкание, и значение возвращается через некоторое время. В течение этого периода я снова вызываю это закрытие с другими данными. Проблема в том, что получен ответ на закрытие, но также получен предыдущий ответ на закрытие. Как я могу удалить ссылку на первое закрытие, чтобы я мог получить ответ только от последнего закрытия?
Вот мой код:
func getUsers() {
self.getUsers = GetUsers()
self.getUsers.getUsersData(latitude: Double(latitude)!, longitude: Double(longitude)!, range:range)
{ (usersArray, error) in
}
}
Обновить:
Я передал текущий объект из замыкания, и, похоже, он работает нормально. Вот обновленный код:
func getUsers() {
self.getUsers = GetUsers()
self.getUsers.getUsersData(latitude: Double(latitude)!, longitude: Double(longitude)!, range:range)
{[weak self] (usersArray, error, getUsersObject) in
if let strongSelf = self {
if strongSelf.getUsers != getUsersObject {
return
}
}
}
}
Если возвращаемый объект из замыкания не соответствует повторно инициализированному объекту, я просто возвращаю его.
Ответ №1:
Это будет зависеть от реализации getUsersData
. В общем, вероятно, нет способа отменить обратный вызов. Лучшее, что вы можете сделать, это заставить код обратного вызова проверять какой-то флаг или идентификатор при его запуске и ничего не делать, если проверка завершается неудачей.
Пример:
ids.append("do this one")
delay(2) { [weak self] in
let id = "do this one"
if let s = self, s.ids.contains(id) {
print(id)
}
}
ids.append("don't do this one")
delay(2) { [weak self] in
let id = "don't do this one"
if let s = self, s.ids.contains(id) {
print(id)
}
}
ids.remove(at:1) // cancel this one
Выводит «Я сделаю это», но не выводит «не делайте этого». Это было бы, но мы отменили это, удалив его из ids
массива.
Комментарии:
1. Я повторно инициализирую, используя self.getUsers = getUsers() . Это должно удалить ссылку на предыдущее замыкание, потому что объект теперь другой. Разве нет?
2. Нет, я не понимаю, почему это будет иметь какой-либо эффект. Закрытие было отправлено
getUsersData
и запланировано для обратного вызова давно. Вы не можете получить к нему доступ отсюда. Более того, закрытие является закрытием, поэтому любая среда, которую оно захватило, остается захваченной.3. Я обновил свой ответ. Это работает. Но правильно ли это делать?
4. Ну, по сути, это то, что я сказал сделать: сопоставить с чем-то в текущем состоянии. Очень приятно. Единственная проблема заключается в том, что вы захватываете
self
, что может привести к утечке памяти. Вы заметите, что я был осторожен, чтобы не делать этого.5. Спасибо за помощь! Я снова обновил свой ответ. Так ли это должно быть сделано?