Jak mogę sprawić, by mój kod czekał do zakończenia zadania w DispatchQueue? Czy potrzebuje jakiegoś CompletionHandler czy czegoś takiego?
func myFunction() {
var a: Int?
DispatchQueue.main.async {
var b: Int = 3
a = b
}
// wait until the task finishes, then print
print(a) // - this will contain nil, of course, because it
// will execute before the code above
}
Używam Xcode 8.2 i piszę w Swift 3.
swift
multithreading
asynchronous
swift3
grand-central-dispatch
Bartosz Woźniak
źródło
źródło
wait
podejścia (jeśli blokowanie nie stanowi dla ciebie problemu, tj. Jeśli nie jesteś w głównym wątku), albo zapewnij procedurę obsługi zakończenia lub użyj metody powiadamiania w klasie wywołującej.group.enter
poza blokiem asynchronicznym? Czy nie powinno być obowiązkiem każdego bloku wchodzenie i opuszczanie grupy?wait
czeka, ażenter
ileave
połączenia są zrównoważone. Jeśli umieściszenter
zamknięcie,wait
nie będzie czekał, ponieważenter
nie został jeszcze wywołany, a zatem liczbaenter
ileave
połączenia są zrównoważone (# enter == 0, # leav == 0).XCTTestExpectation
Zamiast tego użyj s. Zobacz ten przykładowy kodW Swift 3 nie ma potrzeby obsługi zakończenia, gdy
DispatchQueue
kończy jedno zadanie. Ponadto możesz osiągnąć swój cel na różne sposobyOto jeden sposób:
Będzie czekać, aż pętla się zakończy, ale w tym przypadku główny wątek zostanie zablokowany.
Możesz też zrobić to samo:
I ostatnia rzecz: jeśli chcesz używać CompleteHandler po zakończeniu zadania przy użyciu DispatchQueue, możesz użyć
DispatchWorkItem
.Oto przykład użycia
DispatchWorkItem
:źródło
Użyj grupy wysyłkowej
źródło
DispatchQueue.global().async{}
nie zablokuje głównej kolejki.Wersja Swift 5 rozwiązania
func myCriticalFunction () {var value1: String? var value2: String?
}
źródło
Szybki 4
W takich sytuacjach można użyć funkcji Async. Kiedy używasz
DispatchGroup()
, czasami może wystąpić zakleszczenie .źródło