有人可以在这种情况下为我解释 dispatch_async() [英] Can someone explain dispatch_async() for me in this scenario

查看:39
本文介绍了有人可以在这种情况下为我解释 dispatch_async()的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在一个单独的类中有以下方法:

I had the following method in a separate class:

class API: NSObject {

    var data = NSData()
    var delegate: APIProtocol?

    func getItems(callback: (Array<Image>) -> ()) {
        let urlPath: NSString = "http://localhost:3000/files"
        let url = NSURL(string: urlPath)

        let request = NSMutableURLRequest(URL: url)
        request.HTTPMethod = "GET"
        request.addValue("application/json", forHTTPHeaderField: "Accept")

        let config = NSURLSessionConfiguration.defaultSessionConfiguration() as NSURLSessionConfiguration
        let session = NSURLSession(configuration: config) as NSURLSession

        var dataTask = NSURLSessionDataTask()
        dataTask = session.dataTaskWithRequest(request) { (data, response, error) in
            if (error == nil) {
                println("API at URL \(url)")

                let responseArray = NSJSONSerialization.JSONObjectWithData(data, options: .MutableContainers, error: nil) as NSArray
                var images = Image[]()
                for item: AnyObject in responseArray {
                    var location = Image(dict: item as NSDictionary)
                    images.append(location)
                }
                var img = images[0] as Image
                callback(images)

                //self.delegate?.didReceiveResponse(responseArray)
            }

        }
        dataTask.resume()
    }
}

callback() 中调用 self.tableView.reloadData() 时,我无法让我的 tableView 重新加载,直到我添加围绕它的 dispatch_async().

I couldn't get my tableView to reload when calling self.tableView.reloadData() inside the callback() until I added the dispatch_async() around it.

我的问题是:

1) 为什么没有它就不能工作,现在它正确地刷新了 tableView 对我来说是正确的吗?

1) Why wouldn't it work without it and is it the proper thing for me to do now that it's refreshing the tableView correctly?

2) 有没有另一种方法可以让它工作而不必在主队列中添加调度?

2) Is there another way to get it working without having to add the dispatch on the main queue?

api.getItems() { (theArray) in
    dispatch_async(dispatch_get_main_queue(), {
        self.images = theArray
        self.tableView.reloadData()
        if (viaPullToRefresh) {
            self.refreshControl.endRefreshing()
        }
    })
}

推荐答案

在创建 NSURLSession 时,您可以指定委托/完成队列.如果不指定队列

When creating a NSURLSession you can specify the delegate/completion queue. If you don't specify a queue

会话创建一个串行操作队列来执行所有委托方法调用和完成处理程序调用.

the session creates a serial operation queue for performing all delegate method calls and completion handler calls.

所以这意味着您的回调是在私有串行队列上调用的.现在,必须在主队列上更新所有 UI,这就是 tableView.reloadData() 不起作用的原因.

So this means that your callbacks are called on a private serial queue. Now, all UI must be updated on the main queue, this is why tableView.reloadData() wasn't working.

要删除对 main_queue 的调度调用,请像这样创建会话

To remove the dispatch call to the main_queue create the session like this

let session = NSURLSession(configuration: NSURLSessionConfiguration.defaultSessionConfiguration(), delegate: nil, delegateQueue: NSOperationQueue.mainQueue())

这篇关于有人可以在这种情况下为我解释 dispatch_async()的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆