当前位置: 首页 > 面试题库 >

NSURLConnection sendAsynchronousRequest不能从封闭中获取变量

水睿
2023-03-14
问题内容

我正在尝试使用POST从PHP页面获得简单的文本响应。我有以下代码:

func post(url: String, info: String) -> String {
    var URL: NSURL = NSURL(string: url)!
    var request:NSMutableURLRequest = NSMutableURLRequest(URL:URL)
    var output = "Nothing Returned";
    request.HTTPMethod = "POST";
    var bodyData = info;
    request.HTTPBody = bodyData.dataUsingEncoding(NSUTF8StringEncoding);

    NSURLConnection.sendAsynchronousRequest(request, queue: NSOperationQueue.mainQueue()){

        response, data, error in

        output = (NSString(data: data, encoding: NSUTF8StringEncoding))!


    }

    return output
}

虽然这段代码不会引发任何错误,但是当我这样调用它时:

println(post(url, info: data))

即使我更改了该行,它也只会打印:“什么也没返回”:

output = (NSString(data: data, encoding: NSUTF8StringEncoding))!

对此:

println((NSString(data: data, encoding: NSUTF8StringEncoding)))

它确实打印出正确的响应。我的变量在这里做错了吗?


问题答案:

这是在调用使用完成处理程序块/关闭的异步函数。因此,您需要在自己的代码中使用完成处理程序模式。这包括将方法的返回类型更改为,Void并添加一个新的completionHandler闭包,该闭包将在异步调用完成后被调用:

func post(url: String, info: String, completionHandler: (NSString?, NSError?) -> ()) {
    let URL = NSURL(string: url)!
    let request = NSMutableURLRequest(URL:URL)
    request.HTTPMethod = "POST"
    let bodyData = info
    request.HTTPBody = bodyData.dataUsingEncoding(NSUTF8StringEncoding);

    NSURLConnection.sendAsynchronousRequest(request, queue: NSOperationQueue.mainQueue()) { response, data, error in
        guard data != nil else {
            completionHandler(nil, error)
            return
        }

        completionHandler(NSString(data: data!, encoding: NSUTF8StringEncoding), nil)
    }
}

或者,由于NSURLConnection现在已正式弃用,因此最好使用NSURLSession

func post(url: String, info: String, completionHandler: (NSString?, NSError?) -> ()) -> NSURLSessionTask {
    let URL = NSURL(string: url)!
    let request = NSMutableURLRequest(URL:URL)
    request.HTTPMethod = "POST"
    let bodyData = info
    request.HTTPBody = bodyData.dataUsingEncoding(NSUTF8StringEncoding);

    let task = NSURLSession.sharedSession().dataTaskWithRequest(request) { data, response, error in
        dispatch_async(dispatch_get_main_queue()) {
            guard data != nil else {
                completionHandler(nil, error)
                return
            }

            completionHandler(NSString(data: data!, encoding: NSUTF8StringEncoding), nil)
        }
    }
    task.resume()

    return task
}

您这样称呼它:

post(url, info: info) { responseString, error in
    guard responseString != nil else {
        print(error)
        return
    }

    // use responseString here
}

// but don't try to use response string here ... the above closure will be called
// asynchronously (i.e. later)

注意,为简单起见,我采用了尾随闭包语法(请参见Swift编程语言:Closures的
尾随闭包
部分),但希望它能说明这一思想:您不能立即返回异步方法的结果,因此请提供一个完成处理程序关闭,将在异步方法完成后调用。



 类似资料:
  • 问题内容: 我在解析中进行了查询,并获取了GeoPoint坐标数组。这是在封闭内部完成的。我只能访问该闭包内的数组值。我需要能够使用这些值,以便它们可以用作地图上的注释,但我无法使用它们。有人可以告诉我如何从闭包中获取数组值。 码: 问题答案: 在闭包表达式外部而不是内部声明为var。当将其分配给闭包内时,该更改将反映在闭包外的变量中。这称为“捕获” 。捕获外部上下文是使闭包不仅仅是函数的原因。

  • 问题内容: 我有一些这样的代码: 而且我收到警告,因为使用in闭包是可变变量,所以可能会引起问题。 我该如何避免呢?我的意思是我如何将不可变变量发送给回调,因为这是一个for循环,并且我无法更改代码?换句话说,如何将参数传递给闭包? 问题答案: 您需要创建一个范围以使用自执行功能正确捕获。这是因为整个for循环是一个作用域,也就是说,每次循环都捕获相同的变量。因此,回调将以错误的id结尾,因为的值

  • 问题内容: 我正在阅读Java中的匿名类,它说您可以访问封闭类的方法,但不能访问局部变量。为什么会这样呢?我在说这个: 编辑:较旧的示例是不正确的,不能反映我的意思。根据在“访问封闭类的成员”一节中所写的内容,这应该是一个更好的示例,网址为http://docs.oracle.com/javase/tutorial/java/javaOO/localclasses.html。 那么这个限制解决了什

  • 问题内容: 如果我有: 有没有办法找到将要使用的绑定?我看了看,但无法确定某些内容是否适用。换句话说,我可以定义以下内容: 问题答案: 您不必在这里使用该模块。 在Python 2.7中工作

  • 我面临以下问题:我必须给成千上万的图形用户界面元素命名。如果它能像这样工作,那就太好了: 如果我能将元素的名称设置为“Classname.myMenuItem”,那就太好了。 是否有任何方法来获取变量的名称(变量名称ofc,而不是JMenuItem.getName())?

  • 问题内容: 出于教育目的,我尝试制作一个服务器和一个客户端,其中服务器从多个客户端接收数据并回显每条消息。问题是,当我尝试让服务器一次将回显发送到所有客户端时。 我搜寻并回答了许多类似的问题,但是没有一个对我有帮助。希望你能指出我的错误。提前致谢。 问题答案: 您的嵌套类需要外部类的一个实例,因为它不是静态的-但你不 具备 外部类的一个实例。 尝试制作两个嵌套类。看起来他们无论如何都不 需要 引用