channel用于协程之间的通讯,使用send和receive往通道里写入或者读取数据,2个方法为非阻塞挂起函数,channel是热流,不管有没有订阅者都会发送。
1.Channel的使用
val channel = Channel<Int>()
launch {
channel.send(100)
}
launch {
println("receive:" + channel.receive())
}
打印 receive:100
Channel 默认的缓存容量buffer是0,send是个挂起函数,发送到通道,如果通道buffer已满,就会挂起send发送者函数。
如下所示:
val channel = Channel<Int>()
launch {
channel.send(100)
println("sendbefore:200")
channel.send(200)
println("sendafter:200")
channel.send(333)
}
launch {
println("receive:" + channel.receive())
}
打印
receive:100
sendbefore:200
channel.send(200) 发送到通道后,通道满了,发送者的协程send函数被挂起,所以 println("sendafter:200")不执行了。
recevie调用时,如果通道里不为空,就从通道里把元素拿出来,并且从通道里删除元素,如果通道元素为空,则挂起接收者协程即receive函数执行,等通道有元素后 才会执行。
例如:
val channel = Channel<Int>()
launch {
delay(3000)
channel.send(100)
}
launch {
println("receive:before")
println("receive:" + channel.receive())
println("receive:after")
}
输出:
receive:before
receive:100
receive:after
同时receive:before和 receive:100 间隔了3秒
channel的四种缓冲策略
Rendezvous: channel(默认类型): 0尺寸buffer,send是个挂起函数,发送到通道,如果通道buffer已满,就会挂起调用者,这个0buffer,发送一个,如果没人接收,调用者就被挂起
Buffered channel:指定元素大小,发送当buffer满了后Send会被挂起。
Conflated channel: 新元素会覆盖旧元素,receiver只会得到最新元素,Send永不挂起。
Unlimited channel: buffer无限,Send不被挂起。
使用方式:val rendezvousChannel = Channel<Int>(Channel.RENDEZVOUS)
网友评论