在go语言中select关键字的用法及使用场景示例
Go  /  管理员 发布于 1年前   425
在Go语言中,select关键字可用于监听和 channel 有关的 IO 操作。
通过 select 语句,我们可以同时监听 channel,并在其中任意一个 channel 就绪多个时进行相应的处理。
下面看看select 语句的常见用法及场景,以及在使用过程中的注意事项。
select的基本语法如下:
select {
case <-channel1:
// 通道 channel1 就绪时的处理逻辑
case data := <-channel2:
// 通道 channel2 就绪时的处理逻辑
default:
// 当没有任何通道就绪时的默认处理逻辑
}
看到这个语法,很容易想到 switch 语句,虽然 select 语句和 switch 语句表面上有些相似,但它们的用途和功能是不同的。
switch 用于条件判断,而 select 用于通道操作,不能在 select 语句中使用任何类型的条件表达式,只能对通道进行操作。
select的使用规则:
虽然语法简单,但是在使用过程中,还是有一些地方需要注意,我总结了以下四点:
1. select 该语句仅用于通道操作选择,用于在多个通道之间进行,
以监听通道的就绪状态,而不用于其他类型的条件判断。
2. select 语句可以包含多个 case 子句,每个 case 子句对应一个通道操作。
当其中任意一个通道适合时,相应的 case 子句就会被执行。
3. 如果多个通道都已经就绪,select 语句会随机选择一个通道来执行。
这样保证了多个通道之间的公平竞争。
4. select 语句的执行可能是阻塞的,也可能是非阻塞的。
如果没有任何一个通道就绪且没有默认的 default 子句,select 语句会阻塞,直到有一个通道就绪。
如果有 default 子句,且没有任何通道就绪,则语句会阻塞,直到有一个通道就绪 select。
会执行 default 子句,从而避免阻塞。
select的多路复用:
select 最常见的用途之一,同时监听通道,并根据它们的多个就绪状态执行不同的操作。
package main
import (
"fmt"
"time"
)
func main() {
c1 := make(chan string)
c2 := make(chan string)
go func() {
time.Sleep(3 * time.Second)
c1 <- "one"
}()
go func() {
time.Sleep(3 * time.Second)
c2 <- "two"
}()
select {
case msg := <-c1:
fmt.Println(msg)
case msg := <-c2:
fmt.Println(msg)
}
}
执行上面的代码,程序会随机打印 one 或者 two,如果通道为空的话,程序就会一直阻塞在那里
select的阻碍非通信:
当通道中没有数据中断或者没有缓冲空间可写入时,普通的读写器操作将会阻塞。
但通过 select 语句,我们可以在没有数据完整性时默认执行的逻辑,避免程序陷入无限等待状态。
package main
import (
"fmt"
)
func main() {
channel := make(chan int)
select {
case data := <-channel:
fmt.Println("Received:", data)
default:
fmt.Println("No data available.")
}
}
执行上面的代码,程序会执行 default 分支。
输出:
No data available.
select的超时处理:
通过结合 select 和 time.After 函数,我们可以在指定期限等待通道就绪,超过时间后执行相应的逻辑。
package main
import (
"fmt"
"time"
)
func main() {
channel := make(chan int)
select {
case data := <-channel:
fmt.Println("Received:", data)
case <-time.After(3 * time.Second):
fmt.Println("Timeout occurred.")
}
}
执行上面代码,如果 channel 在 3 秒内没有数据裁决,select 会执行 time.After 分支。
输出:
Timeout occurred.
123 在
Clash for Windows作者删库跑路了,github已404中评论 按理说只要你在国内,所有的流量进出都在监控范围内,不管你怎么隐藏也没用,想搞你分..原梓番博客 在
在Laravel框架中使用模型Model分表最简单的方法中评论 好久好久都没看友情链接申请了,今天刚看,已经添加。..博主 在
佛跳墙vpn软件不会用?上不了网?佛跳墙vpn常见问题以及解决办法中评论 @1111老铁这个不行了,可以看看近期评论的其他文章..1111 在
佛跳墙vpn软件不会用?上不了网?佛跳墙vpn常见问题以及解决办法中评论 网站不能打开,博主百忙中能否发个APP下载链接,佛跳墙或极光..路人 在
php中使用hyperf框架调用讯飞星火大模型实现国内版chatgpt功能示例中评论 教程很详细,如果加个前端chatgpt对话页面就完美了..
Copyright·© 2019 侯体宗版权所有·
粤ICP备20027696号