【问题标题】:Swift lazy load property Alamofire requestSwift 延迟加载属性 Alamofire 请求
【发布时间】:2015-11-01 13:54:08
【问题描述】:

我正在尝试使用 Alamofire 请求延迟加载属性 (UIImage)。这就是我所在的位置:

public lazy var theImage: UIImage = MyCalass.loadImage { (imageTest) -> Void in
    return imageTest
}

class public func loadImage(completion: (imageTest: UIImage) -> Void){
    Alamofire.request(.GET, "http://pathtoimage/image.jpg").response { (request, response, data, error) in
        var tempImage = UIImage(data: data!, scale:1)
        completion(imageTest: tempImage!)
    }
}

错误:'()' 不能转换为 'UIImage'

【问题讨论】:

  • loadImage(_:) 没有返回值(即Void,又名());您正在尝试将 UIImage 类型的惰性属性分配给不返回图像的函数的返回值。
  • 对于像请求图像这样的异步任务,惰性或计算属性不是合适的解决方案。
  • 方法调用很简单,我只是在尝试延迟加载
  • 为什么要让它变得懒惰?它不一定会出现,或者你会在什么条件下显示它?
  • 嗨,凯尔,看看我的回答,我相信它会对你有所帮助 :-)

标签: ios swift asynchronous lazy-loading alamofire


【解决方案1】:

嘿伙计,用 GCD 很容易解决...

像这样建立一个类:

class AsynchImageLoader {
    class func loadImageAsync (imageURL: NSURL, completionHandler: (downloadedImage: UIImage?) -> Void) {
        dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_BACKGROUND, 0), { () -> Void in
            if let imageData: NSData = NSData(contentsOfURL: imageURL) {
                if let imageImage: UIImage = UIImage(data: imageData) {
                    dispatch_async(dispatch_get_main_queue(), { () -> Void in
                        completionHandler(downloadedImage: imageImage)
                    })
                } else {
                    dispatch_async(dispatch_get_main_queue(), { () -> Void in
                        completionHandler(downloadedImage: nil)
                    })
                }
            } else {
                dispatch_async(dispatch_get_main_queue(), { () -> Void in
                    completionHandler(downloadedImage: nil)
                })
            }
        })
    }
}

然后像这样加载您的图像...

let imageView: UIImageView = UIImageView()
        AsynchImageLoader.loadImageAsync(NSURL(string: "yourURL")!, completionHandler: { (downloadedImage) -> Void in
            imageView.image = downloadedImage
        })

downloadedImage 可能为 nil,如果出现问题...否则您可以将其放入您的视图、数组或任何您想要的...

顺便说一句...惰性修饰符并不意味着图像是“惰性/异步”加载的...在Swift中,您可以将某些东西声明/初始化为惰性,这意味着它将在其初始化时声明类,但它会在你第一次尝试在代码中访问它之前不久被初始化......这可能是任何时候,甚至永远不会:-)

或者从此更改您的代码...

public lazy var theImage: UIImage = MyCalass.loadImage { (imageTest) -> Void in
    return imageTest
}

到这里……

var theImage: UIImage? 
MyCalass.loadImage { (imageTest) -> Void in
    theImage = imageTest
}

【讨论】:

    【解决方案2】:

    如果你正在使用图像,我建议你使用类似DLImageLoader 的东西,它可以与 CocoaPods 一起安装,加载图像只需使用

    DLImageLoader.sharedInstance().displayImageFromUrl("\(thumbnailUrl)", imageView: myImageView)
    

    这样你的图片在下载完成后加载,其他选项也要勾选,有一些带有回调的,但上面的例子是最简单的

    如果您在应用程序中多次需要图像,它甚至会使用缓存,我有它的实现并且效果很好,我也有 Alamofire。当我更换了曾经有这种图像下载管理的 AFNetworking 后,我就得到了这个补充

    【讨论】:

      【解决方案3】:

      您不必使用 Alamofire 来加载图像。你可以让它异步。

      你可以做这样的事情,包括关闭:

      lazy var theImage: UIImage = {
          var sampImage = getImage({ (image) in
              return image
          })
      }()
      
      func getImage(completion: UIImage -> ()) {
          var newImage: UIImage?
      
          let priority = DISPATCH_QUEUE_PRIORITY_DEFAULT
          dispatch_async(dispatch_get_global_queue(priority, 0)) {
              let url = NSURL(string: "http://pathtoimage/image.jpg")
              let data = NSData(contentsOfURL: url!)
              newImage =  UIImage(data: data!)!
      
              completion(newImage!)
          }
      }
      

      编辑:我能够使用下面的代码成功地将图像加载到 Playground 文件中。之前的问题是请求是异步的,由于某种原因导致它无法正确返回。

      import UIKit
      
      class Example {
      
          lazy var theImage: UIImage = {
      
              var newImage: UIImage?
      
              let url = NSURL(string: "http://2.bp.blogspot.com/-XJbC3jA7cOo/VW2ItW5aRjI/AAAAAAAACcc/_f_WhTEXvFQ/s1600/testPattern.png")
              let data = NSData(contentsOfURL: url!)
              newImage =  UIImage(data: data!)!
      
              println(data)
      
              return newImage!
          }()
      
          init() {}
      }
      
      var exp = Example()
      
      exp.theImage
      

      我认为延迟加载的属性中不允许函数调用

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2017-12-28
        • 2013-07-03
        • 2014-07-26
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多