go 缓冲channel和非缓冲channel的区别

在Go中我们make一个channel有两种方式,分别是有缓冲的和没缓冲的

非缓冲和缓冲

  • 缓冲channel即buffer channel创建方式为make(chan TYPE,SIZE)

    ch := make(chan int, 10) // 缓冲通道

  • 非缓冲channel即unbuffer channel创建方式为make(chan TYPE)

    ch2 := make(chan int, 0) //非缓冲通道
    ch := make(chan int) //非缓冲通道

非缓冲和缓冲

  • 非缓冲channel,channel发送和接收动作是同时发生的
  • 缓冲channel类似一个队列,只有队列满了才可能发送阻塞

代码示例

非缓存chan

func main() {
    ch := make(chan int)
    ch <- 1
    go func(){
        i := <-ch
        println(i)
    }
} 这样看似没毛病!but运行之后引发异常fatal error: all goroutines are asleep - deadlock! 就是因为 ch<-1 发送了,但是同时没有接收者,所以就发生了阻塞。   但如果我们把 ch <- 1 放到go func()下面,程序就会正常运行。  

缓冲chan

func main() {
    ch := make(chan int,1)
    ch <- 1
    ch <- 2
    go func(){
        i := <-ch
        println(i)
    }
    time.Sleep(1 * time.Millisecond)
}

同样引发异常。what!!!channel的大小为1,而我们要往里面塞2个数据,所以就会阻塞住。
可以增加chan容量,或者在go func()之后运行写入数据。

总结

显式调用close(ch),可以阻塞数据写入,但是还可以取数据。

Life is more than the present.