Jaka jest różnica między uruchomieniem / dołączeniem a asynchronicznym / oczekującym w koroutinach Kotlin

W bibliotece kotlinx.coroutines możesz rozpocząć nowy coroutine używając launch (z join) lub async (z await). Jaka jest między nimi różnica?

Author: Roman Elizarov, 2017-09-14

2 answers

  • launch służy do [[13]}odpalania i zapominania o coroutine. To jak zakładanie nowego wątku. Jeśli kod wewnątrz launch kończy się z wyjątkiem, to jest traktowany jak uncaught wyjątek w wątku - zwykle drukowany na stderr w backend aplikacji JVM i zawiesza aplikacje na Androida. join służy do oczekiwania na zakończenie uruchomionego coroutine i nie propaguje jego wyjątku. Jednak rozbite dziecko coroutine anuluje również swój rodzic z odpowiednim wyjątkiem.

  • async jest używany do uruchomienia koroutine, który oblicza jakiś wynik. Wynik jest reprezentowany przez instancję Deferred a Ty musisz używać await robi się. Nieużywany wyjątek wewnątrz kodu async jest przechowywany wewnątrz wynikowego Deferred i nie jest dostarczany nigdzie indziej, zostanie po cichu upuszczony, chyba że zostanie przetworzony. nie wolno zapominać o koroutine zacząłeś od async .

 80
Author: Roman Elizarov,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-09-18 07:25:16

Znajduję ten poradnik https://github.com/Kotlin/kotlinx.coroutines/blob/master/coroutines-guide.md być użytecznym. Przytoczę najważniejsze części

Coroutine

Zasadniczo koroutiny są nićmi lekkimi.

Więc możesz myśleć o coroutine jako o czymś, co zarządza wątkiem w bardzo skuteczny sposób.

Start

fun main(args: Array<String>) {
    launch { // launch new coroutine in background and continue
        delay(1000L) // non-blocking delay for 1 second (default time unit is ms)
        println("World!") // print after delay
    }
    println("Hello,") // main thread continues while coroutine is delayed
    Thread.sleep(2000L) // block main thread for 2 seconds to keep JVM alive
}

Więc launch uruchamia wątek w tle, robi coś i zwraca token natychmiast jako Job. Możesz wywołać join na tym Job, aby zablokować, dopóki ten launch wątek nie zakończy się

fun main(args: Array<String>) = runBlocking<Unit> {
    val job = launch { // launch new coroutine and keep a reference to its Job
        delay(1000L)
        println("World!")
    }
    println("Hello,")
    job.join() // wait until child coroutine completes
}

Async

Koncepcyjnie async jest jak launch. Rozpoczyna oddzielną koronę, która jest lekką nicią, która działa jednocześnie ze wszystkimi innymi koronami. Różnica polega na tym, że launch zwraca zadanie i nie niesie żadnej wynikowej wartości, podczas gdy async zwraca odroczoną -- lekką, nieblokującą przyszłość, która reprezentuje obiecaj, że dostarczysz wynik później.

Więc async uruchamia wątek w tle, robi coś i natychmiast zwraca token jako Deferred.

fun main(args: Array<String>) = runBlocking<Unit> {
    val time = measureTimeMillis {
        val one = async { doSomethingUsefulOne() }
        val two = async { doSomethingUsefulTwo() }
        println("The answer is ${one.await() + two.await()}")
    }
    println("Completed in $time ms")
}

Możesz użyć .wait () na wartości odroczonej, aby uzyskać jej ostateczny wynik, ale Deferred jest również zadaniem, więc możesz ją anulować w razie potrzeby.

Więc Deferred jest w rzeczywistości Job. Zobacz też https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.experimental/-deferred/index.html

interface Deferred<out T> : Job (source)

Async domyślnie jest chętny

Istnieje możliwość asynchronizacji za pomocą opcjonalnego parametru start o wartości CoroutineStart.Leniwy. Uruchamia się tylko wtedy, gdy jego wynik jest potrzebny przez niektórych lub gdy wywołana jest funkcja start.

 19
Author: onmyway133,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-01-03 14:50:24