Swift:在闭包中传递来自不同范围的值

Posted

技术标签:

【中文标题】Swift:在闭包中传递来自不同范围的值【英文标题】:Swift: passing values from different scopes in closures 【发布时间】:2017-03-23 11:50:41 【问题描述】:

晚上,我正在从 API 获取数据,但在通过不同范围传递泥瓦匠时遇到了问题:

我的控制器很有趣:

func getDaily() 
    let json = NetworkManager.getDaily()
    print(json)

而这个在 NetworkManager 类中

class func getDaily() -> JSON 
    //Setting the url for the request
    let url = "\(base_url)planetary/apod?api_key=\(apy_key)"
    var json: JSON = []
    //Making the request
    Alamofire.request(url, method: .get).validate().responseJSON response in
        switch response.result 
        case .success(let value):
            json = JSON(value)
            //print("JSON: \(json)")
        case .failure(let error):
            print(error)
        
    

    return json

显然,第一个 func 中的 json 打印始终为空。

你能解释一下如何做到这一点吗?

【问题讨论】:

【参考方案1】:

您的函数 getDaily() 不应返回 JSON。因为这是一个异步请求,所以您需要一个回调。试试这样:

class func getDaily(result: @escaping (JSON) -> ()) 
    //Setting the url for the request
    let url = "\(base_url)planetary/apod?api_key=\(apy_key)"
    var json: JSON = []
    //Making the request
    Alamofire.request(url, method: .get).validate().responseJSON response in
        switch response.result 
        case .success(let value):
            json = JSON(value)
            result(json)
        case .failure(let error):
            print(error)
        
    

你的来电者会变成:

func getDaily() 
    NetworkManager.getDaily  json in
        print(json)
    

【讨论】:

你的代码给我这个错误“不能调用非函数类型'DataResponse'的值” 对不起,是因为我使用的“response”参数名与Alamofire的response参数冲突。【参考方案2】:

对我来说这是正确的方法:

import UIKit
import Alamofire

class APIManager: NSObject 
    static let sharedInstance = APIManager()

    //TODO :-
    /* Handle Time out request alamofire */


    func requestGETURL(_ strURL: String, success:@escaping (JSON) -> Void, failure:@escaping (Error) -> Void)
    
        Alamofire.request(strURL).responseJSON  (responseObject) -> Void in
            //print(responseObject)
            if responseObject.result.isSuccess 
                let resJson = JSON(responseObject.result.value!)
                //let title = resJson["title"].string
                //print(title!)
                success(resJson)
            

            if responseObject.result.isFailure 
                let error : Error = responseObject.result.error!
                failure(error)
            
        
    

    func requestPOSTURL(_ strURL : String, params : [String : AnyObject]?, headers : [String : String]?, success:@escaping (JSON) -> Void, failure:@escaping (Error) -> Void)
        Alamofire.request(strURL, method: .post, parameters: params, encoding: JSONEncoding.default, headers: headers).responseJSON  (responseObject) -> Void in

            if responseObject.result.isSuccess 
                let resJson = JSON(responseObject.result.value!)
                success(resJson)
            
            if responseObject.result.isFailure 
                let error : Error = responseObject.result.error!
                failure(error)
            
        
    



/********************************* To get response in another class ********************************/

 APIManager.sharedInstance.requestPOSTURL(HttpsUrl.Address, params: dict as [String : AnyObject]?, headers: nil, success:  (json) in
 // success code
 print(json)
 , failure:  (error) in
 //error code
 print(error)
 )

【讨论】:

以上是关于Swift:在闭包中传递来自不同范围的值的主要内容,如果未能解决你的问题,请参考以下文章

将值从闭包赋值给变量 Swift

根据您来自的类(Swift)为变量赋予不同的值

无法通过 DiscordJS 中的不同范围传递变量

在 Swift 3 中附加一个函数范围之外的变量

如何在 Swift 中正确获取 Do-Catch 范围之外的值(使用 Try)

来自提供的范围依赖的传递依赖