Ang DispatchQueue ay isang pangunahing pila ng framework na Grand Central Dispatch (GCD) para sa pamamahala ng mga asynchronous na gawain sa iOS at macOS. Ayon sa Apple Developer Documentation, 2026, ang DispatchQueue ay nag-aabstrak ng pamamahala ng thread mula sa developer sa pamamagitan ng serial at concurrent na mga pila. Awtomatikong namamahagi ang GCD ng mga gawain sa system thread pool, inaalis ang manu-manong paglikha at pagwasak ng mga thread.
Mga pangunahing punto
DispatchQueue ay isang bagay ng framework na Grand Central Dispatch (GCD) na namamahala sa pagpapatupad ng mga gawain sa system o custom na mga pila ng thread. Ang Grand Central Dispatch ay isang mababang antas na aklatan ng Apple, magagamit mula noong iOS 4 at macOS 10.6, na ganap na nag-aabstrak ng pamamahala ng thread mula sa developer. Gumagamit ang GCD ng thread pool ng operating system at awtomatikong nag-scale ng bilang ng mga thread sa ilalim ng load ng device.
Hindi kailangan ng developer na manu-manong lumikha at magwasak ng mga thread — GCD ang pumapalit sa gawaing ito, na nagbibigay ng simpleng API sa pamamagitan ng DispatchQueue. Ang gawain sa anyo ng closure ay ipinapadala sa pila sa pamamagitan ng mga pamamaraang sync o async. Sa unang kaso, ang tumatawag na thread ay naba-block hanggang sa makumpleto ang gawain, sa pangalawa — agad na nagpapatuloy sa pagpapatupad.
Ayon sa Apple (2026), ang GCD ay gumagamit ng system thread pool na umaangkop sa bilang ng mga core at kasalukuyang load ng processor. Ang concurrent na pila ay hindi lumilikha ng bagong thread para sa bawat gawain — muling ginagamit ng GCD ang mga thread mula sa pool, na nagpapaliit ng overhead sa paglikha ng thread.
Ang Grand Central Dispatch ay binubuo ng tatlong pangunahing bahagi: ang pila (DispatchQueue), ang grupo (DispatchGroup), at ang semaphore (DispatchSemaphore). Ang pila ay ang pangunahing elemento na tumatanggap ng mga gawain sa anyo ng mga bloke ng code. Pinag-synchronize ng DispatchGroup ang pagpapatupad ng maraming gawain, at nililimitahan ng DispatchSemaphore ang access sa isang shared resource sa isang tiyak na bilang ng mga thread.
Ang bawat pila ng GCD ay nauugnay sa isang partikular na klase ng QoS (Quality of Service) na nagpapaalam sa system tungkol sa kahalagahan ng gawain. Ginagamit ng system ang QoS para sa pamamahagi ng oras ng processor sa pagitan ng mga pila, na nagbibigay ng priyoridad sa mas kritikal na mga gawain — halimbawa, pag-update ng UI o pagproseso ng mga pagpindot ng user.
Serial na pila ay nagsasagawa ng mga gawain nang mahigpit na sunud-sunod, isa-isa. Kung tatlong gawain ang ilalagay sa serial na pila, ang pangalawa ay magsisimula lamang pagkatapos ng ganap na pagkumpleto ng una. Ginagamit ang serial na mga pila para sa pag-synchronize ng access sa mga shared resource — halimbawa, sa isang array na binabago mula sa maraming bahagi ng code.
Concurrent na pila ay nagpapatakbo ng maraming gawain nang sabay-sabay, ipinamamahagi ang mga ito sa mga available na thread mula sa system pool. Ang mga gawain sa concurrent na pila ay nagsisimula sa pagkakasunud-sunod ng pagdating (FIFO), ngunit nagtatapos sa arbitraryong pagkakasunud-sunod kung magkaiba ang oras ng pagpapatupad. Concurrent na pila ay hindi ginagarantiyahan ang pagkakasunud-sunod ng pagkumpleto — tanging ang pagkakasunud-sunod ng pagsisimula.
| Parameter | Serial na pila | Concurrent na pila |
|---|---|---|
| Pagkakasunud-sunod ng pagpapatupad | Mahigpit na sunud-sunod | Magkatulad |
| Bilang ng mga thread | Isa | Marami mula sa pool ng GCD |
| Paggamit | Proteksyon ng shared resource | Malayang pag-compute |
| Main queue | Oo (pangunahing thread) | Hindi |
| Panganib ng deadlock | Mataas sa sync sa parehong pila | Mababa |
Ang serial na pila ay mainam para sa mga gawain na nagbabago ng shared state — pagsulat sa file, pag-update ng modelo ng data, o pagtatrabaho sa Core Data. Ang paggamit ng serial na pila ay ginagarantiyang ang dalawang bahagi ng code ay hindi sabay na magbabago ng parehong data, inaalis ang kondisyon ng karera nang walang karagdagang pagla-lock.
Concurrent na pila ay angkop para sa mga gawaing hindi nakadepende sa isa't isa: pag-load ng maraming larawan, parallel na network request, o batch processing ng data. Awtomatikong nagpapasya ang GCD kung gaano karaming gawain ang sabay na patakbuhin, batay sa bilang ng mga core ng processor at kasalukuyang load ng system.
QoS (Quality of Service) — mekanismo ng GCD na nagpapaalam sa operating system tungkol sa kahalagahan at pagka-apura ng gawain. Ginagamit ng system ang QoS para sa pag-iskedyul ng mga thread: ang mga gawain na may mas mataas na QoS ay nakakakuha ng mas maraming oras ng processor at mas maagang nasisimulan. Ang halaga ng QoS ay ipinapadala kapag lumilikha ng pila o nagpapadala ng partikular na gawain.
Sa GCD, limang klase ng QoS ang available. .userInteractive — pinakamataas na priyoridad para sa mga gawaing nauugnay sa UI. .userInitiated — para sa mga gawaing pinasimulan ng user. .utility — para sa mga gawain sa background na may pagpapakita ng progreso. .background — para sa mga gawaing hindi nakikita ng user. .default — antas sa pagitan ng userInitiated at utility, ginagamit bilang default.
Ayon sa Apple (2026), ang maling pagpili ng QoS ay isa sa mga karaniwang sanhi ng mga problema sa performance. Ang pagpapatakbo ng background download na may QoS .userInteractive ay kumukuha ng mga mapagkukunan mula sa UI, na nagdudulot ng micro-lag sa mga animation. Inirerekomenda na piliin ang pinakamababang QoS na nagbibigay pa rin ng katanggap-tanggap na oras ng pagpapatupad.
Kapag nag-load ng larawan para sa agarang pagpapakita, gamitin ang .userInitiated — inaasahan ng user ang resulta. Para sa preloading ng susunod na screen, sapat na ang .utility. Ang background synchronization sa server ay isinasagawa gamit ang .background, na pinapaliit ang epekto sa mga aktibong gawain.
DispatchGroup ay nagbibigay-daan sa pagsubaybay sa pagkumpleto ng isang grupo ng mga gawain. Kapag ang lahat ng gawain sa grupo ay natapos, tinatawag ng GCD ang notify handler sa tinukoy na pila. Ito ay lalong kapaki-pakinabang kapag naglo-load ng maraming independiyenteng mapagkukunan — data ng profile, listahan ng kaibigan, at mga setting — kapag ang interface ay kailangang i-update lamang pagkatapos matanggap ang lahat ng data.
Sinusuportahan ng DispatchGroup ang synchronous na tawag na wait() na nagba-block sa kasalukuyang thread hanggang sa makumpleto ang lahat ng gawain. Ito ay maginhawa kapag ang code ay hindi maaaring magpatuloy nang wala ang mga resulta ng grupo. Ang asynchronous na variant — notify() — ay tumatawag sa closure sa tinukoy na pila pagkatapos ng pagkumpleto ng lahat ng gawain, nang hindi nagba-block sa tumatawag na thread.
DispatchSemaphore ay kumokontrol sa access sa isang resource, na nililimitahan ang bilang ng sabay-sabay na pag-access. Ang semaphore na may paunang halaga na 3 ay nagpapahintulot sa pagpapatakbo ng hindi hihigit sa tatlong parallel na gawain. Kapag tinawag ang wait(), bumababa ang counter, kapag signal() — tumataas. Kung ang counter ay zero, ang thread ay naba-block hanggang sa mapalaya ang resource.
Tingnan natin ang tatlong praktikal na halimbawa ng paggamit ng DispatchQueue sa Swift. Ang una ay nagpapakita ng pangunahing async na tawag na may pagbabalik sa pangunahing thread, ang pangalawa — pag-synchronize sa pamamagitan ng serial na pila, ang pangatlo — DispatchGroup para sa parallel na mga request.
DispatchQueue.main ay ang serial na pila ng pangunahing thread, na eksklusibong inilaan para sa mga operasyon ng UI. Palaging gamitin ito para sa pag-update ng interface pagkatapos makumpleto ang background work.
let queue = DispatchQueue.global(qos: .userInitiated)
queue.async {
let data = self.fetchData()
DispatchQueue.main.async {
self.updateUI(with: data)
}
}
Ang paglikha ng iyong sariling serial na pila na may natatanging identifier ay nag-synchronize ng access sa isang mutable array. Lahat ng read at write operation ay dumadaan sa isang pila, inaalis ang kondisyon ng karera.
let serialQueue = DispatchQueue(label: "com.app.items")
var items: [Int] = []
serialQueue.async {
items.append(1)
}
serialQueue.async {
let last = items.last
DispatchQueue.main.async {
print("Last item: \(last)")
}
}
DispatchGroup ay nagpapahintulot sa pagpapatakbo ng maraming gawain sa isang concurrent na pila at pagtanggap ng abiso kapag lahat ay natapos na. Ito ay kapaki-pakinabang kapag naglo-load ng data para sa screen ng profile.
let group = DispatchGroup()
let worker = DispatchQueue.global()
worker.async(group: group) { self.loadProfile() }
worker.async(group: group) { self.loadFriends() }
worker.async(group: group) { self.loadSettings() }
group.notify(queue: DispatchQueue.main) {
self.showCompleteUI()
}
Deadlock sa sync na tawag sa isang serial na pila — ang pinakakaraniwang pagkakamali. Kung ang isang gawain sa isang serial na pila ay tumawag ng queue.sync sa parehong pila, ang thread ay permanente naba-block. Ang pila ay naghihintay ng pagkumpleto ng kasalukuyang gawain, at ang gawain ay naghihintay ng pagkumpleto ng sync na tawag — isang klasikong mutual deadlock.
Lahat ng operasyon sa UIKit ay dapat isagawa sa pangunahing thread. Nakikita ng Xcode ang mga pagkakamaling ito sa Debug mode sa pamamagitan ng Main Thread Checker. Sa Release build, humahantong ang mga ito sa hindi mahuhulaan na pag-uugali: hindi tumatakbo ang mga animation, hindi naa-update ang UI, posible ang mga crash.
Ang paglikha ng daan-daang custom na pila sa halip na global na mga pila ay isang anti-pattern. Bawat pila ay kumokonsumo ng mga system resources. Para sa karamihan ng mga gawain, sapat na ang global na concurrent na mga pila na may iba't ibang QoS at isa-dalawang serial na pila para sa pag-synchronize ng shared data.
Kapag nagsasagawa ng resource-intensive cyclic na mga gawain sa isang background na pila nang walang autoreleasepool, ang memorya ay lumalaki hanggang sa matapos ang buong loop. Ang ARC ay naglalabas ng mga object lamang kapag lumalabas sa autorelease pool. Balutin ang mga iteration ng loop sa autoreleasepool { } para sa napapanahong pagpapalaya ng memorya.
Mga madalas itanong
OperationQueue ay binuo sa ibabaw ng GCD, ngunit nagbibigay ng mas mataas na antas ng API na may mga dependency ng operasyon, KVO, at suporta sa pagkansela. Ang DispatchQueue ay isang mababang antas na pila para sa simpleng async na mga gawain nang walang pamamahala ng dependency.
Hindi sinusuportahan ng GCD ang paghinto ng isang tumatakbong gawain. Ang pamamaraang suspend() ay nagpa-pause lamang ng mga bagong gawain, ang kasalukuyang gawain ay tumatakbo hanggang sa matapos. Para sa pagkansela, kailangan ang manu-manong pagsusuri ng flag sa loob ng code ng gawain.
Para sa pangunahing request na may agarang pagpapakita ng resulta — .userInitiated. Para sa preloading ng data — .utility. Para sa background synchronization — .background.
Hindi itinatakda ng GCD ang bilang ng mga thread. Ang thread pool ay dynamic na nag-scale sa ilalim ng load, isinasaalang-alang ang mga core ng processor, kasalukuyang load, at QoS ng bawat gawain. Ang maximum na bilang ay nililimitahan ng system.
Ang UIKit ay hindi thread-safe — lahat ng mga klase nito ay dapat tawagin lamang mula sa pangunahing thread. Ang paglabag ay nagdudulot ng hindi mahuhulaan na pag-uugali, mga na-miss na update, at mga crash sa produksyon.
Buod
Gagawa kami ng mobile application na turnkey
Gumagawa ang IT Sectr ng mga iOS at Android application para sa mga startup at negosyo mula noong 2017. Magpapayo kami sa iyo at magmumungkahi ng pinakamahusay na solusyon.
Basahin din