如何在单线程中使用actor频繁处理消息?
How to use actors to handle message frequently in a single thread?
我需要在单个非 UI 线程中频繁启动一些代码。我正在尝试使用演员来实现它:
class SomeClass {
@OptIn(ObsoleteCoroutinesApi::class)
private fun CoroutineScope.myActor() = actor<MyMessage> {
for (message in channel) {
delay(5000)
Log.d("SomeClass", "Message ${Thread.currentThread().name}")
}
}
private var channel: SendChannel<MyMessage>? = null
private val scope = CoroutineScope(Dispatchers.Default)
fun send() {
scope.launch {
if (channel == null) {
channel = myActor()
}
channel?.send(IncCounter)
}
}
sealed class MyMessage
}
然后调用它:
覆盖乐趣 onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
val c = SomeClass()
c.send()
c.send()
c.send()
c.send()
}
输出:
Message DefaultDispatcher-worker-8
Message DefaultDispatcher-worker-2
Message DefaultDispatcher-worker-8
Message DefaultDispatcher-worker-2
因此,正如我所见,它创建了多个线程。如何在单线程中实现频繁的消息处理?
尝试在CoroutineDispatcher
上使用limitedParallelism(1)
功能:
private val scope = CoroutineScope(Dispatchers.Default.limitedParallelism(1))
或
private fun CoroutineScope.myActor() = actor<MyMessage>(context = Dispatchers.Default.limitedParallelism(1)) { ... }
我需要在单个非 UI 线程中频繁启动一些代码。我正在尝试使用演员来实现它:
class SomeClass {
@OptIn(ObsoleteCoroutinesApi::class)
private fun CoroutineScope.myActor() = actor<MyMessage> {
for (message in channel) {
delay(5000)
Log.d("SomeClass", "Message ${Thread.currentThread().name}")
}
}
private var channel: SendChannel<MyMessage>? = null
private val scope = CoroutineScope(Dispatchers.Default)
fun send() {
scope.launch {
if (channel == null) {
channel = myActor()
}
channel?.send(IncCounter)
}
}
sealed class MyMessage
}
然后调用它:
覆盖乐趣 onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState)
val c = SomeClass()
c.send()
c.send()
c.send()
c.send()
}
输出:
Message DefaultDispatcher-worker-8
Message DefaultDispatcher-worker-2
Message DefaultDispatcher-worker-8
Message DefaultDispatcher-worker-2
因此,正如我所见,它创建了多个线程。如何在单线程中实现频繁的消息处理?
尝试在CoroutineDispatcher
上使用limitedParallelism(1)
功能:
private val scope = CoroutineScope(Dispatchers.Default.limitedParallelism(1))
或
private fun CoroutineScope.myActor() = actor<MyMessage>(context = Dispatchers.Default.limitedParallelism(1)) { ... }