kotlin - 从 CoroutineScope 启动的 Job 和 SupervisorJob 也是一个 SupervisorJob 吗?

标签 kotlin kotlin-coroutines

在下面的例子中。 childJob 是 SupervisorJob 吗?

val viewModelScope: CoroutineScope = CoroutineScope(Dispatchers.Main + SupervisorJob())
val childJob = viewModelScope.launch {/* do something */}

或者类似的东西是必要的:

val viewModelScope: CoroutineScope = CoroutineScope(Dispatchers.Main + SupervisorJob())
val childJob = viewModelScope.launch(SupervisorJob()) {/* do something */}

最佳答案

我会让代码来说话:

fun main() = runBlocking {
    val scopeSupervisor = SupervisorJob()
    val explicitSupervisor = SupervisorJob()
    val explicitPlainJob = Job()
    val scope = CoroutineScope(Dispatchers.Main + scopeSupervisor)

    scopeSupervisor.printJobClass("scopeSupervisor")
    explicitPlainJob.printJobClass("explicitPlainJob")
    println()
    scope.launch {
        coroutineContext.printJobClass("context 1")
        scopeSupervisor.printChildren("scopeSupervisor")
    }.join()
    scope.launch(explicitSupervisor) {
        coroutineContext.printJobClass("context 2")
        explicitSupervisor.printChildren("explicitSupervisor")
    }.join()
    scope.launch(explicitPlainJob) {
        coroutineContext.printJobClass("context 3")
        explicitPlainJob.printChildren("explicitPlainJob")
    }.join()
}

fun CoroutineContext.printJobClass(msg: String) {
    println("$msg class: ${this[Job]!!.className}")
}

fun Job.printChildren(msg: String) {
    println("$msg children: ${children.map { it.className }.joinToString()}")
}

val Any.className get() = this::class.java.simpleName

这会打印

scopeSupervisor class: SupervisorJobImpl
explicitPlainJob class: JobImpl

context 1 class: StandaloneCoroutine
scopeSupervisor children: StandaloneCoroutine
context 2 class: StandaloneCoroutine
explicitSupervisor children: StandaloneCoroutine
context 3 class: StandaloneCoroutine
explicitPlainJob children: StandaloneCoroutine

解读:

范围内的作业和显式传入的作业都不会成为与协程关联的作业。协程作业始终为 StandaloneCoroutine 类型,并且它是传入作业的子级。

另请注意,传入不是作用域作业子级的显式 SupervisorJob 是错误的。如果您取消范围内的顶级作业,这不会传播到您创建的显式 SupervisorJob

关于kotlin - 从 CoroutineScope 启动的 Job 和 SupervisorJob 也是一个 SupervisorJob 吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59084084/

相关文章:

android - 通过 `Dispatchers.IO` 启动协程时出现 NetworkOnMainThreadException

java - 从工件的 .jar 运行时找不到 Kotlinx 协程类

kotlin - 首次运行时未定义的迭代器值

android - 使用协程更新 UI 异步调用

android - 如何在不定义类的情况下使用 moshi 创建复杂的 json?

for-loop - 为什么在 Kotlin 中删除了索引 for 循环?

java - OkHttp CookieJar 向请求添加 cookie 失败

android - 图书馆 billing.ktx 促进了什么 "idiomatic Kotlin"?

android - 对包含两种数据类的 ArrayList<Any> 进行排序

android - 单元测试新的 Kotlin 协程 StateFlow