考虑下面的代码,我尝试使用Executors.newFixedThreadPool(1).asCoroutineDispatcher()
创建一个单线程分派程序;我希望launch(singleThread){...}
中的代码按顺序执行
预期的结果应该如下所示,因为异步块#2首先到达/获取singleThread。
异步块#2 异步块#1 单线程块#2 单线程块#1 答案是3
但实际结果是
异步块#2 异步块#1 单线程块#1 单线程块#2 答案是3
单线程块#2和单线程块#1似乎是并行运行的,singleThread在这里没有什么不同。
import java.util.concurrent.Executors
import kotlinx.coroutines.*
import kotlin.system.*
val singleThread = Executors.newFixedThreadPool(1).asCoroutineDispatcher()
fun main() = runBlocking<Unit> {
val time = measureTimeMillis {
val one = async { // async block #1
delay(200)
println("async block #1")
launch (singleThread) {
delay(500)
println("single thread block #1")
}
2
}
val two = async { // async block #2
delay(100)
println("async block #2")
launch (singleThread) {
delay(1500)
println("single thread block #2")
}
1
}
println("The answer is ${one.await() + two.await()}")
}
println("Completed in $time ms")
}
发布于 2019-03-01 11:21:14
请注意,代码中的delay()
是suspend
函数。它是通过协同悬挂来实现的。这意味着代码的执行在调用delay
时暂停,并且只在超时之后才继续执行。线程(例如,您通过async(singleThread) {..}
使用的线程)并不忙着等待时间的流逝。
总体情况如下
singleThread
上运行。delay(1500)
挂起,singleThread
是空闲的。singleThread
上启动delay(500)
挂起,singleThread
是空闲的。delay(500)
delay(1500)
resume(500)
计划在singleThread
中运行任务1的第二部分resume(1500)
计划在singleThread
中运行任务2的第二部分发布于 2021-12-27 21:21:16
除了@EugenePetrenko的答案之外,这是一个新的方法CoroutineDispatcher.limitedParallelism(numberOfParallelism)
,您可以使用它来保证并行性限制--最多可以在这个调度程序中并发执行一个协同。它将看起来像:
val singleThread = Dispatchers.IO.limitedParallelism(1)
someCoroutineScope.launch (singleThread) {
...
}
函数limitedParallelism
可以从1.6.0版本的kotlinx.coroutines
库开始。
https://stackoverflow.com/questions/54942872
复制相似问题