Kotlin中如何在suspend函数返回后立即执行指定代码
Kotlin 中suspend函数执行完成后链式调用指定代码块的实现方法
可以实现,有原生语法和自定义API两种方案,均符合协程执行语义,能保证变量x在代码块执行前已经完成赋值。
方案1:直接使用Kotlin标准库扩展(无需额外封装)
Kotlin自带的also/apply标准扩展函数天生支持该需求,suspend函数的执行是严格顺序的,只有loadSomething完全执行完成后才会进入also代码块:
suspend fun loadSomething() { // 内部加载逻辑,执行完成后会给x赋值 x = loadDataFromNetwork() } // 调用示例 loadSomething().also { // 此处loadSomething已执行完成,x已经完成赋值,可以直接使用 println("加载完成,x的值为:$x") }
如果需要处理加载过程中的异常,可以搭配runCatching使用:
runCatching { loadSomething() } .onSuccess { /* 加载成功,可正常使用x */ } .onFailure { e -> /* 加载失败,处理异常 */ }
方案2:自定义whenDone扩展实现你要的链式API
如果你希望严格实现你提到的loadSomething().whenDone{ }调用形式,可以自己写一个通用扩展函数:
// 通用whenDone扩展,支持任意返回值的suspend函数,代码块运行在当前协程上下文 suspend fun <T> T.whenDone(action: suspend (T) -> Unit): T { action(this) return this }
定义完成后即可按你期望的方式调用:
loadSomething().whenDone { // 此处x已经完成赋值,可直接使用 println("加载完成,x的值为:$x") }
注意事项
- 以上两种方案的代码块都和
loadSomething运行在同一个协程上下文,遵循结构化并发规则,不会额外启动协程 - 如果需要
whenDone内的逻辑异步执行不阻塞当前协程,可以在代码块内自行用launch启动子协程 - 如果
loadSomething执行过程中抛出未捕获异常,后续代码块不会执行,符合正常的异常传播逻辑
内容的提问来源于stack exchange,提问作者Nico
相关产品推荐
相关产品推荐

