设为首页 加入收藏

TOP

Go基础系列:channel入门(三)
2018-11-20 00:14:18 】 浏览:375
Tags:基础 系列 channel 入门
e v1 := <-ch1: ... // ch2有数据时,读取到v2变量中 case v2 := <-ch2: ... // 所有case都不满足条件时,执行default default: ... }

defalut语句是可选的,不允许fall through行为,但允许case语句块为空块。select会被return、break关键字中断。

select的行为模式主要是对channel是否可读进行轮询,但也可以用来向channel发送数据。它的行为如下:

  • 如果所有的case语句块都被阻塞,则阻塞直到某个语句块可以被处理
  • 如果多个case同时满足条件,则随机选择一个进行处理
  • 如果存在default且其它case都不满足条件,则执行default。所以default必须要可执行而不能阻塞

需要注意的是,如果在select中执行send操作,则可能会永远被send阻塞。所以,在使用send的时候,应该也使用defalut语句块,保证send不会被阻塞

一般来说,select会放在一个无限循环语句中,一直轮询channel的可读事件。

下面是一个示例,pump1()和pump2()都用于产生数据(一个产生偶数,一个产生奇数),并将数据分别放进ch1和ch2两个通道,suck()则从ch1和ch2中读取数据。然后在无限循环中使用select轮询这两个通道是否可读,最后main goroutine在1秒后强制中断所有goroutine。

package main

import (
    "fmt"
    "time"
)

func main() {
    ch1 := make(chan int)
    ch2 := make(chan int)
    go pump1(ch1)
    go pump2(ch2)
    go suck(ch1, ch2)
    time.Sleep(1e9)
}
func pump1(ch chan int) {
    for i := 0; i <= 30; i++ {
        if i%2 == 0 {
            ch <- i
        }
    }
}
func pump2(ch chan int) {
    for i := 0; i <= 30; i++ {
        if i%2 == 1 {
            ch <- i
        }
    }
}
func suck(ch1 chan int, ch2 chan int) {
    for {
        select {
        case v := <-ch1:
            fmt.Printf("Recv on ch1: %d\n", v)
        case v := <-ch2:
            fmt.Printf("Recv on ch2: %d\n", v)
        }
    }
}
首页 上一页 1 2 3 4 下一页 尾页 3/4/4
】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
上一篇casbin-权限管理 下一篇go 交叉编译,部署

最新文章

热门文章

Hot 文章

Python

C 语言

C++基础

大数据基础

linux编程基础

C/C++面试题目