Quelqu'un peut-il expliquer la différence entre eux? Je pense que la portée fournit une référence (par exemple, Job) pour les annuler et le contexte fournit une référence au thread sous-jacent. Est-ce vrai?
Portée
Chaque générateur de coroutine (comme le lancement, l'async, etc.) et chaque fonction de portée (comme coroutineScope, withContext, etc.) fournit sa propre portée avec sa propre instance de Job dans le bloc interne de code qu'il exécute. Par convention, ils attendent tous que toutes les coroutines de leur bloc soient terminées avant de s'achever, renforçant ainsi la discipline de la concurrence structurée.
Contexte
Les coroutines s'exécutent toujours dans un contexte qui est représenté par la valeur du type CoroutineContext, définie dans la bibliothèque standard de Kotlin.
Le contexte coroutine est un ensemble de divers éléments. Les principaux éléments sont le travail de la coroutine, que nous avons vu auparavant, et son répartiteur, qui est couvert dans cette section.
Oui, en principe vous avez raison, voici plus de détails.
Portée
viewModelScope
dans Android) pour éviter les fuitesContexte
Le contexte détermine sur quel thread les coroutines s'exécuteront. Il y a quatre options:
Dispatchers.Default
- pour un travail intense sur le processeur (par exemple, trier une grande liste)Dispatchers.Main
- ce que ce sera dépend de ce que vous avez ajouté aux dépendances d'exécution de vos programmes (par exemple kotlinx-coroutines-Android
, pour le fil d'interface utilisateur dans Android)Dispatchers.Unconfined
- exécute les coroutines non confinées sur aucun thread spécifiqueDispatchers.IO
- pour les gros travaux IO (par exemple, requêtes de base de données de longue durée)L'exemple suivant rassemble à la fois la portée et le contexte. Il crée une nouvelle étendue dans laquelle les coroutines s'exécuteront (si elles ne sont pas modifiées) sur un thread désigné pour le travail IO) et les annule via leur étendue.
val scope = CoroutineScope(context = Dispatchers.IO)
val job = scope.launch {
val result = suspendFunc1()
suspendFunc2(result)
}
// ...
scope.cancel() // suspendFunc1() and suspendFunc2() will be cancelled