Call UIView related calls from within the completi

2019-06-25 04:20发布

问题:

I am calling the following Class method from within my ViewController init method:

[NSURLConnection sendAsynchronousRequest:urlrequest 
                                   queue:opQueue 
                       completionHandler:^(NSURLResponse *response, NSData *data, NSError*error){


// Update an NSMutableArray (an Instance variable

[self tableView] reloadData]; // is this ok to call?
}];

This code working as intended and tableView refreshes appropriately, My concern: is this call thread safe?. is it ok to access an UI element from the completion block?

Thanks,

Vinod

回答1:

Actually, this is not correct unless opQueue happens to be +[NSOperationQueue mainQueue]

That completion block will be scheduled on the queue you provide. In your case, you're calling that queue 'opQueue'. If that queue is being drained by some thread other than the main thread, then you shouldn't make that call to reload the tableview there.

You should instead do whatever processing you need to do and then enqueue another block on the main queue which calls the reload.

^(NSURLResponse *response, NSData *data, NSError*error){

   // Do some processing work in your completion block

   dispatch_async(dispatch_get_main_queue(), ^{

    // Back on the main thread, ask the tableview to reload itself.
    [someTableView reloadData];

   });
}

Or if the processing is light and quick (and fixed amount of time), then just pass the mainQueue as the 'opQueue';

I hope that makes sense. A lot of good information to be found here: Concurrency Programming Guide



回答2:

It is thread safe. Very much because you are not using threads. The completion handler is just called later, not on a separate thread.