9

In iOS, we have GCD and Operation to handle concurrent programming.

looking into GCD we have QoS classes, and they're simple and straight forward, this question is about why DispatchQueue.main.async is commonly used to asynchronies X tasks in the Main Thread.

So when we usually handle updating something in the UI we usually use that function since to prevent any irresponsiveness from the application.

makes me think is writing code inside the UIViewController usually executed in the main thread ?

but also knowing that callback & completionHandler usually execute without specifying on what thread they are in, and the UI never had a problem with that !! so it is on the background ?

How Swift handles this ? and what thread am i writing on by default without specifying anything ?

Mohmmad S
  • 5,001
  • 4
  • 18
  • 50
  • while you also can be certain iOS makes all lifecycle / user interaction related calls on the main thread, usually you can be certain in one more thing: a callback or completion closure (or block) __might not be__ invoked on a main thread – unless the API specifies the behaviour explicitly (e.g. _executed on main thread_, _executed concurrently_, etc...). – holex Mar 06 '19 at 09:48
  • how the compiler decide that ? normally and writing in `UIViewController` by default execute the code in the main thread ? – Mohmmad S Mar 06 '19 at 09:51
  • 2
    I believe every class that starts with UI, like UIViewController is by default executed on the main thread, what I'm not sure is that if I create an NSObject for exemple, is it executed on the main thread aswell ? – Mathias Mar 06 '19 at 09:54
  • @Mathias good point – Mohmmad S Mar 06 '19 at 09:55
  • 3
    This depends on where the `NSObject` is created. For example, if you are creating this in the @IBAction function for a button click, yes it is created in the main thread. On the other hand, if you call from a completion handler of a URLSession request which returns in a background thread, it will be created in a background thread (as long as you didn't dispatch to main thread using `DispatchQueue.main.async`). The context(thread) in which you write your code will determine on what thread the code executes – jms Mar 06 '19 at 10:00
  • "is writing code inside the UIViewController usually executed in the main thread?" What do you mean by mentioning "insider the UIViewController"? "but also knowing that callback & completionHandler usually execute without specifying on what thread they are in" who said that?! Do you know how things implemented in the background? "and what thread am i writing on by default without specifying anything ?" Main Thread. – Ahmad F Mar 06 '19 at 13:30
  • @AhmadF inside the class, i don't specify any thread they work on and never seen such code, so Main thread is the default – Mohmmad S Mar 06 '19 at 13:32
  • @AhmadF how the callbacks are handled automatically not causing any problem to the UI ? – Mohmmad S Mar 06 '19 at 13:34
  • Indeed it is, the main thread. Depends on what do you mean by "callbacks", don't consider that using a method from the UIKit -for instance- with a callback means that its not including `DispatchQueue.main.async` in it. – Ahmad F Mar 06 '19 at 13:38
  • its not included, lets talk about completion handlers – Mohmmad S Mar 06 '19 at 13:39
  • How the compiler recognize that he doesn't have to wait for the CompH , what is the mechanic behind that – Mohmmad S Mar 06 '19 at 13:40

1 Answers1

6

Since there are more than one question here, let's attempt to answer them one by one.

why DispatchQueue.main.async is commonly used to asynchronies X tasks in the Main Thread.

Before mentioning a direct answer, make sure that you don't have confusion of understanding:

  • Serial <===> Concurrent.
  • Sync <===> Async.

Keep in mind that DispatchQueue.main is serial queue. Using sync or async has nothing to do with determining serialization or currency of a queue, instead they refer to how the task is handled. Thus saying DispatchQueue.main.async means that:

returns control to the current queue right after task has been sent to be performed on the different queue. It doesn't wait until the task is finished. It doesn't block the queue.

cited from: https://stackoverflow.com/a/44324968/5501940 (I'd recommend to check it.)

In other words, async means: this will happen on the main thead and update it when it is finished. That's what makes what you said:

So when we usually handle updating something in the UI we usually use that function since to prevent any irresponsiveness from the application.

seems to be sensible; Using sync -instead of async- will block the main.


makes me think is writing code inside the UIViewController usually executed in the main thread ?

First of all: By default, without specifying which thread should execute a chunk of code it would be the main thread. However your question seems to be unspecific because inside a UIViewController we can call functionalities that are not executed on the main thread by specifying it.


but also knowing that callback & completionHandler usually execute without specifying on what thread they are in, and the UI never had a problem with that !! so it is on the background ?

"knowing that callback & completionHandler usually execute without specifying on what thread they are in" No! You have to specify it. A good real example for it, actually that's how Main Thread Checker works.

I believe that there is something you are missing here, when dealing when a built-in method from the UIKit -for instance- that returns a completion handler, we can't see that it contains something like DispatchQueue.main.async when calling the completion handler; So, if you didn't execute the code inside its completion handler inside DispatchQueue.main.async so we should assume that it handles it for you! It doesn't mean that it is not implemented somewhere.

Another real-world example, Alamofire! When calling

Alamofire.request("https://httpbin.org/get").responseJSON { response in
    // what is going on here work has to be async on the main thread
}

That's why you can call it without facing any "hanging" issue on the main thread; It doesn't mean its not handled, instead it means they handle it for you so you don't have to worry about it.

Ahmad F
  • 30,560
  • 17
  • 97
  • 143