【问题标题】:Chaining closures and completion handlers Swift 3链接闭包和完成处理程序 Swift 3
【发布时间】:2017-10-16 07:37:29
【问题描述】:

我很难理解使用闭包链接完成处理程序的工作原理。

我正在使用的示例如下:

typealias CompletionHandler = (_ result: AnyObject?, _ error: NSError?) -> Void
func getRequestToken(completionHandler: CompletionHandler){
    taskForGET(path: "PathToWebsite.com") { (result, error) in
        if let error = error {
            print(error)
        } else {
            print(result)
        }
    }
}

func taskForGET(path: String, completionHandler: CompletionHandler) {
    //URLSESSIONCODE with completion handler
    (data, response, error) {
        if let error = error {
            CompletionHandler(result: nil, error: error)
        } else {
            let data = data
            parseJSON(data: data, completionHandler: completionHandler)
        }
    }

}
func parseJSON(data: NSData, completionHandler: CompletionHandler) {
    //SerializingJSON with do catch block
    do {
        completionHandler(result: theResult, error: nil)
    } catch {
        completionHandler(result: nil, error: error)
    }
}

所以基本上这段代码的作用是启动一个对服务器的 GET 请求。如果 GET 请求发回数据,则将其解析为 JSON。如果在此过程中的任何时候发生故障,它会返回错误。

我基本上明白这里发生了什么,但我不明白完成处理程序是如何被触发的。

第一个 taskForGET 被调用,它有一个完成处理程序作为可以返回结果或错误的参数,我知道了。

下一步是调用 parseJSON,其中传递来自 taskForGET 的数据,然后传递的完成处理程序是 taskForGET 的完成处理程序。我完全不明白。

然后在 parseJSON 中,完成处理程序通过从其参数调用完成处理程序返回 JSON 或错误。在这种情况下是 taskForGET 的完成处理程序?

我不明白流程。即使我们成功解析了 JSON,调用 taskForGET 的结果又是如何返回到 getRequestToken 的。

对此的任何帮助将不胜感激。

【问题讨论】:

  • 老实说,我建议对涉及链接超过 1 个的任何进程使用完成处理程序。在我看来,使用 Promise 或 DispatchQueue 会更简单。

标签: swift closures completionhandler


【解决方案1】:

只有一个完成处理程序从一种方法传递到另一种方法。

让我们单独声明处理程序,顺便说一句。在 Swift 3 中省略类型别名中的参数标签:

typealias CompletionHandler = (Any?, Error?) -> Void

let handler : CompletionHandler = { (result, error) in
    if let error = error {
        print(error)
    } else {
        print(result)
    }
}

这个闭包应该在进程结束时执行。现在getRequestToken 方法看起来像

func getRequestToken(completionHandler: CompletionHandler){
    taskForGET(path: "PathToWebsite.com", completionHandler: handler)
}

处理程序/闭包作为参数从getRequestToken 传递到taskForGET,然后从taskForGET 传递到parseJSON,但它始终是同一个对象。

【讨论】:

  • 好吧,这就是我产生巨大困惑的地方。我不认为它是一个被传递的物体。非常感谢,这非常有帮助!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-02-24
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多