在协程中执行IO绑定函数(例如,从后端请求数据)可以让我暂停执行,直到请求的结果可用,对吧?然而,一个受CPU限制的函数(例如,解析一个巨大的文本文件)并不“等待”任何东西,它只是做了大量的工作。那么,在协程中执行它不是给了我暂停执行它的好处吗?当涉及到CPU绑定函数时,协程给我的唯一(有价值的)优势是能够选择在执行函数时将被阻塞的线程(或线程池),我说的对吗?
发布于 2019-05-07 02:46:03
所以,在协程中执行它,不是给了我暂停执行它的好处吗?,
,the,does,the,the,,its,its,不是吗?
我不确定我明白你的意思,但是调用一个挂起的函数无论如何都会挂起调用协程,不管你选择什么调度程序,据我所知,这并不依赖于函数内部的内容。
但是,请注意,从协程内部调用阻塞函数会使协程阻塞执行它的线程,这里没有魔力。这就是为什么应该在协程中避免阻塞操作的原因。
当涉及到CPU-bound函数时,协程给我的唯一(有价值的)优势是能够选择在执行函数时将被阻塞的线程(或线程池),我说的对吗?
是的,使用Dispachers.IO或Dispatchers.Default只会导致选择不同的线程池。
在IO的情况下,池将根据需要产生尽可能多的线程,因为它们都可以“在I/O上被阻塞”。
在使用Default的情况下,只会创建与核心数量成正比的线程数量,因为受CPU限制的任务没有必要创建比核心更多的线程(如果所有核心都很忙,则上下文切换只会降低整体性能)。
发布于 2019-05-07 05:11:51
挂起函数不会自动使函数不阻塞线程,就像下面的情况一样,因为它仍然会阻塞调用线程(与用于启动协程的作用域相关联的调度程序)
suspend fun findBigPrime(): BigInteger =
BigInteger.probablePrime(4096, Random())挂起函数可以通过使用如下所示的withContext来成为非阻塞线程函数。
suspend fun findBigPrime(): BigInteger =
withContext(Dispatchers.Default) {
BigInteger.probablePrime(4096, Random())
}这会导致从主/调用者线程启动的协程被阻塞,而不是线程本身被阻塞。
https://medium.com/@elizarov/blocking-threads-suspending-coroutines-d33e11bf4761
https://stackoverflow.com/questions/56009668
复制相似问题