非缓冲通道:

make(chan T)一次发送 一次接管 都是阻塞的

缓冲通道:

make(chan T, capacity)发送:缓冲区数据满了才阻塞接管:缓冲区数据空了才接管 

举个例子:

package mainimport (    "fmt"    "strconv")func main() {    //非缓冲通道    ch1 := make(chan int)    fmt.Println(len(ch1), cap(ch1)) //0 0    //缓存通道    ch2 := make(chan int, 5)    ch2 <- 100    ch2 <- 200    ch2 <- 300    ch2 <- 400    ch2 <- 500    fmt.Println(len(ch2), cap(ch2))    fmt.Println("=======================")    ch3 := make(chan string, 4)    //    启动一个子协程 放进去ch3    go sendData(ch3)    for {        v, ok := <-ch3        if !ok {            fmt.Println("Reading completed ")            break        }        fmt.Println("\tthe data read is : ", v)    }    fmt.Println("main-goroutine is finished")}func sendData(ch chan string) {    for i := 0; i < 10; i++ {        ch <- "Data " + strconv.Itoa(i)        fmt.Println("子协程写入第 %d 个数据", i)    }    close(ch)}

运行后果是:

0 05 5=======================子协程写入第 %d 个数据 0子协程写入第 %d 个数据 1子协程写入第 %d 个数据 2子协程写入第 %d 个数据 3子协程写入第 %d 个数据 4        the data read is :  Data 0        the data read is :  Data 1        the data read is :  Data 2        the data read is :  Data 3        the data read is :  Data 4        the data read is :  Data 5子协程写入第 %d 个数据 5子协程写入第 %d 个数据 6子协程写入第 %d 个数据 7子协程写入第 %d 个数据 8子协程写入第 %d 个数据 9        the data read is :  Data 6        the data read is :  Data 7        the data read is :  Data 8        the data read is :  Data 9Reading completed main-goroutine is finished

其实就是缓冲区大小咱们设为4导致的。

参考:bilibili