Ok so I have gone through a ton of questions and answers and I know the understanding of it, but when I am trying some code, I am getting some results that doesnt stand by those theories.
What I understand till now :
This is the part that seems fine. Now comes the tricky part
Eg-
let syncQ = DispatchQueue(label:"xyz") // by default it is serial
syncQ.sync{
for _ in 0...10{
print("ABC")
}
}
syncQ.sync{
for _ in 0...10{
print("XYZ")
}
}
Expected Output : ABC * 10 , XYZ * 10 This is fine.
Now when I introduce concurrent serial Q, the output is same. So my question is as concurrent queues say that tasks will be done in the same time or concurrently, it isnt happening.
Eg -
let syncConc = DispatchQueue(label:"con",attributes:.concurrent)
syncConc.sync{
for _ in 0...10{
print("XYZ")
}
for _ in 0...10{
print("ABC")
}
}
syncConc.sync{
for _ in 0...10{
print("HHH")
}
for _ in 0...10{
print("XXX")
}
}
Output : XYZ *10 ,ABC*10, HHH*10, XXX*10
So it seems that Synchronous Concurrent Queue, act like serial Queues, and only way to make concurrent operations is that if we throw a Asynchronous queue in between the action. So from this I cannot understand, what is the purpose of concurrent type of serial queues.
If anyone can give coded examples, it will be much appreciated, as I already know the theory and working of it. Much appreciated.
The problem is that you're mixing up the queue types and the execution model.
There are serial and concurrent queues, and you can dispatch tasks to both types synchronously or asynchronously.
A queue can be:
And we can submit a task to a queue:
To sum it up:
Actually, It looks like In your code when you are executing the task in concurrent queue (second snippet) you are dispatching the task through sync block, So that will block the current thread as per the sync behaviour.
"Sync : Control will return once all tasks inside the block will be executed.”
let syncConc = DispatchQueue(label:"con",attributes:.concurrent)
syncConc.sync{
for _ in 0...10{
print("XYZ")
}
for _ in 0...10{
print("ABC")
}
}
syncConc.sync{
for _ in 0...10{
print("HHH")
}
for _ in 0...10{
print("XXX")
}
}
So, Here In this case first the suncConc queue will dispatch the first sync block, now since it is blocking call, Next task is not going to be dispatched immediately, It will be dispatched, Once the first will be completed and then It will be dispatched in suncConc queue and again executed with blocking call.
Now, let me come to your query
"Now when I introduce concurrent serial Q, the output is same. So my question is as concurrent queues say that tasks will be done in the same time or concurrently, it isnt happening."
Yes, sync operations can also concurrently perform but It is only possible when you dispatch both the calls immediately without blocking current thread. Check following snippet, The two sync tasks are dispatched from different queue, Hence It will be executed concurrently.
let syncConc = DispatchQueue(label:"con",attributes:.concurrent)
DispatchQueue.global(qos: .utility).async {
syncConc.sync{
for _ in 0...10{
print("XYZ - \(Thread.current)")
}
for _ in 0...10{
print("ABC - \(Thread.current)")
}
}
}
DispatchQueue.global(qos: .userInitiated).async {
syncConc.sync{
for _ in 0...10{
print("HHH - \(Thread.current)")
}
for _ in 0...10{
print("XXX - \(Thread.current)")
}
}
}
Execute the code & See the magic all the theories will be apply as expected :)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With