Ios 如果任务被取消,则不要执行块
我有Ios 如果任务被取消,则不要执行块,ios,swift,block,nsurlsession,nsurlsessiondatatask,Ios,Swift,Block,Nsurlsession,Nsurlsessiondatatask,我有MainViewController->ThumbnailViewController->ImageFullScreenViewController。顾名思义,我有一个主屏幕,从主屏幕转到显示图像集合的屏幕,在选择图像时,我会全屏打开图像 在ThumbnailViewController中,我下载了如下图像 private func getImages() { self.galleryImages.removeAll() for url in urls {
MainViewController
->ThumbnailViewController
->ImageFullScreenViewController
。顾名思义,我有一个主屏幕,从主屏幕转到显示图像集合的屏幕,在选择图像时,我会全屏打开图像
在ThumbnailViewController
中,我下载了如下图像
private func getImages() {
self.galleryImages.removeAll()
for url in urls {
let task = NSURLSession.sharedSession().dataTaskWithURL(url) { (data, response, error) in
// errors are handled
if let image = UIImage(data: data) {
self.galleryImages.append(image!)
}
}
task.resume()
requests.append(task)
}
}
在viewDidLoad()
中,我调用getImages()
。在ThumbnailViewController
的视图将消失()
中,我取消正在进行的任务
override func viewWillDisappear(animated: Bool) {
super.viewWillDisappear(animated)
if isMovingFromParentViewController() {
if requests.count > 0 {
for request in requests {
if request is NSURLSessionDataTask {
let task = request as! NSURLSessionDataTask
task.cancel()
}
}
}
}
}
问题是,当我打开ThumbnailViewController
并立即返回时,如果我立即打开ThumbnailViewController
,在某些情况下,我可以看到相同图像的两个副本(很少,但可以复制)
经过调查,我发现,在视图中取消NSURLSessionDataTask
只会取消任务,而不会取消完成块(这就是行为)。在一些罕见的情况下,会对以前的NSURLSessionDataTask
执行完成块,从而结束与新的NSURLSessionDataTask
的响应混合
我该怎么办
注意:galleryImages
是我在ImageFullScreenViewController
(UIPageViewController
)中重用的单一属性。首先,您应该注意释放ThumbnailViewController
对象。使用弱self
声明捕获列表,它将在99%的情况下消除您的问题(如果您在其他地方没有保留self
),尽管您的模型仍然不能完美地使用该单音
private func getImages() {
self.galleryImages.removeAll()
for url in urls {
let task = NSURLSession.sharedSession().dataTaskWithURL(url) { [weak self] (data, response, error) in
// errors are handled
// replace self. with self?.
if let image = UIImage(data: data) {
self?.galleryImages.append(image!)
}
}
task.resume()
requests.append(task)
}
}
更简单的一点是:)在将图像添加到galleryImages之前,为什么不使用galleryImages.contains(image){…}是galleryImages
computed属性,或者它是否有任何观察者?请出示申报单。没有什么奇怪的,任务有时已经在完成的路上了;奇怪的是,它如何能够在ThumbnailViewController
的新实例中将接收到的图像与图像数组混合。如果galleryImages
以某种方式共享,则可能会发生这种情况。对不起。我应该提一下galleryImages
是一个单件。我将其设置为singleton,因为我在ImageFullScreenViewController
中为UIPageViewController
重用了相同的数组,并按照建议修改了模型,从而解决了问题。非常感谢。除非我误解了您的建议,否则如果单个视图控制器意外地同时启动两次抓取,即使这样也不能保证正常工作。在我看来,一种更稳健的方法是a.在removeAll中用新数组替换GalleryImage,B.将其存储在块外的新变量中,C.在块内捕获该变量,而不是在self.GalleryImage,D.在主线程上运行块的内部,这样就不会有多个线程与单个可变数组发生冲突。这样,每一组请求总是填充一个新数组,并且只使用最新的数组。@dgatwood你说得对。我只是指出了现有代码中的重要问题,以及不完善的模型;我认为建议具体的其他模式过于宽泛