在Swift中检索远程照片时如何防止因连接速度缓慢导致应用程序崩溃或冻结?

时间:2017-10-19 08:16:09

标签: swift

我想通过url字符串在我的表格视图单元格中显示头像图像。当手机没有连接到互联网时会崩溃,所以我添加了Reachability swift。但现在我面临另一个问题,当用户离开wifi区域或互联网连接不稳定时,应用程序将冻结,我无法点击任何东西,直到我走回强大的wifi区域。为什么?

let imageData:NSData = try! NSData(contentsOf: imageUrl)

此代码会崩溃所以我尝试添加do&赶上但仍然没有工作。这是因为应用程序无法连接到url字符串并获取数据以便应用程序将被冻结?如何在检索远程照片时防止因连接速度慢导致应用程序崩溃或冻结?

if Reachability.shared.isConnectedToNetwork(){
    if let crew = user!["crew"] as? [String:Any], let crewAva = crew["crew_avatar"] as? String {
        let imageUrlString = crewAva
        let imageUrl:URL = URL(string: imageUrlString)!

        DispatchQueue.main.async(execute:  {
            do{
                let imageData:NSData = try NSData(contentsOf: imageUrl)
                let image = UIImage(data: imageData as Data)
                self.avaImg.image = image
            }
            catch{
                print("error")
            }
        })
    }
}else{
    print("Not reachable")
}

3 个答案:

答案 0 :(得分:2)

来自Build association with work Items in vNext

  

init?(contentsOf url: URL)

     

重要

     

请勿使用此同步方法来请求基于网络的网址。对于基于网络的URL,此方法可以在慢速网络上阻止当前线程数十秒,从而导致用户体验不佳,而在iOS中,可能会导致应用程序被终止。   相反,对于非文件网址,请考虑使用NSData documentation类的dataTask(with:completionHandler:)方法。有关详细信息,请参阅NSURLSession

答案 1 :(得分:0)

尝试仅更新主线程上的UI。

<span class="spanRight">1234567890</span>

答案 2 :(得分:0)

解决方案

func getDataFromUrl(url: URL, completion: @escaping (Data?, URLResponse?, Error?) -> ()) {
    URLSession.shared.dataTask(with: url) { data, response, error in
        completion(data, response, error)
        }.resume()
}

func downloadImage(url: URL) {
    getDataFromUrl(url: url) { data, response, error in
        guard let data = data, error == nil else { return }
        print(response?.suggestedFilename ?? url.lastPathComponent)
        DispatchQueue.main.async() {
            self.avaImg.image = UIImage(data: data)
        }
    }
}

override func viewWillAppear(_ animated: Bool) {
    if let crew = user!["crew"] as? [String:Any], let crewAva = crew["crew_avatar"] as? String {
        let imageUrlString = crewAva
        let url = URL(string: imageUrlString)!
        downloadImage(url: url)
    }
}