kotlin - 为什么流程不执行,没有引发错误?

标签 kotlin kotlin-coroutines kotlin-flow kotlin-coroutines-flow

GlobalScope或自定义的CoroutineScope实例都不起作用:

import kotlinx.coroutines.*
import kotlinx.coroutines.flow.*

fun makeFlow() = flow {
    println("sending first value")
    emit(1)
    println("first value collected, sending another value")
    emit(2)
    println("second value collected, sending a third value")
    emit(3)
    println("done")
}

@InternalCoroutinesApi
fun main() {
    val someScope = CoroutineScope(Dispatchers.Default)
    someScope.launch {
        makeFlow().collect { value ->
            println("value is $value")
        }
    }
    GlobalScope.launch {
        makeFlow().collect { value ->
            println("value is $value")
        }
    }
}


绝对没有输出或抛出错误

为什么?

甚至更陌生,当我添加一个runBlocking{}块时,一切都会执行:

val someScope = CoroutineScope(Dispatchers.Default)
    someScope.launch {
        makeFlow().collect { value ->
            println("someScope: value is $value")
        }
    }
    GlobalScope.launch {
        makeFlow().collect { value ->
            println("GlobalScope: value is $value")
        }
    }
    runBlocking {
        makeFlow().collect { value ->
            println("runBlocking: value is $value")
        }
    }

输出:
sending first value
sending first value
sending first value
runBlocking: value is 1
GlobalScope: value is 1
first value collected, sending another value
GlobalScope: value is 2
second value collected, sending a third value
GlobalScope: value is 3
done
someScope: value is 1
first value collected, sending another value
someScope: value is 2
second value collected, sending a third value
someScope: value is 3
done
first value collected, sending another value
runBlocking: value is 2
second value collected, sending a third value
runBlocking: value is 3
done

最佳答案

您启动的协程并没有完成,因为main函数在触发它们后立即返回而无需等待它们,从而完成了您的应用程序。没有发生任何错误,因为它是预期的行为。
runBlocking的lambda不会返回,直到其中的所有协程返回为止。在这种情况下,它恰好浪费了足够的时间来让其他两个协程有时间完成,可能是因为它是最后启动的,并且做的工作量差不多。

如果您对前两个延迟,则他们将没有机会完成:

fun main() {
    val someScope = CoroutineScope(Dispatchers.Default)
    someScope.launch {
        delay(100L)
        makeFlow().collect {
            makeFlow().collect { value ->
                println("value is $value")
            }
        }
    }
    GlobalScope.launch {
        delay(100L)
        makeFlow().collect { value ->
            println("value is $value")
        }
    }
    runBlocking {
        makeFlow().collect { value ->
            println("runBlocking: value is $value")
        }
    }
}
sending first value
runBlocking: value is 1
first value collected, sending another value
runBlocking: value is 2
second value collected, sending a third value
runBlocking: value is 3
done

关于kotlin - 为什么流程不执行,没有引发错误?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62204492/

相关文章:

java - kotlin协程可以像java Timer一样使用吗?

android - 如何使用挂起函数作为参数在 View 模型中初始化流

firebase - 名称为 DEFAULT 的 Flutter Firebase 实时数据库 FirebaseApp 不存在。可用的应用程序名称 : [DEFAULT]

android - Kotlin 中 globalScope 、 corountineScope 和 viewScope 的区别

java - RXJava2 阻塞流,直到满足条件

android - 如何在调用方法中检查 Kotlin 协程 job.isActive

android - Compose 使用 Flow<T>.collectAsState render List<T> LazyColumn progressive

android - 有流的房间在空时返回 null

kotlin - 如果 Kotlin 中的 Room 存在数据库,我如何不创建数据库?

android - 如何在房间中自动增加主键?