首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >为什么withContext阻塞后的线会被阻塞?

为什么withContext阻塞后的线会被阻塞?
EN

Stack Overflow用户
提问于 2019-08-23 12:15:49
回答 1查看 68关注 0票数 1

我想知道withContext后面的行(注意:以Dispatchers.IO为第一个参数)是如何被阻塞的。

它们似乎处于不同的线程上,但我想知道协同机制是如何顺序执行它们的。

代码语言:javascript
复制
fun deleteAll() {
     viewModelScope.launch {
         Log.d("tag", "Outside withContext(start): " + Thread.currentThread().name)
         withContext(Dispatchers.IO) {
            Log.d("tag", "Deleting....: " + Thread.currentThread().name)
            delay(3_000)
            Log.d("tag", "Done deleting.")
         }
         Log.d("tag", "Outside withContext(end): " + Thread.currentThread().name)
     }
}

输出:

代码语言:javascript
复制
ViewModel deleteAll returning
Outside withContext(start): main
Deleting....: DefaultDispatcher-worker-5
Done deleting.
Outside withContext(end): main
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2019-08-23 20:59:56

如果您查看withContext的定义,您会注意到它是一个挂起函数:

代码语言:javascript
复制
public suspend fun <T> withContext

挂起函数由Kotlin编译器转换为连续函数。你可以把它看作是一连串的回调。

所以,你会得到这样的东西:

代码语言:javascript
复制
    fun a() {
        Log.d("tag", "Outside withContext(start): " + Thread.currentThread().name)
        fun b() {
            withContext(Dispatchers.IO) {
                Log.d("tag", "Deleting....: " + Thread.currentThread().name)
                delay(3_000)
                Log.d("tag", "Done deleting.")
            }
            fun c() {
                Log.d("tag", "Outside withContext(end): " + Thread.currentThread().name)
            }
        }()
    }()

现在,您可以更清楚地看到,在c()完成之前,不能执行b()

另一种思考方法是查看withContext的代码

代码语言:javascript
复制
...
  block.startCoroutineCancellable(coroutine, coroutine)
  coroutine.getResult()
}

coroutine.getResults()完成之前,其他任何事情都不会发生。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/57626173

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档