This is the 15th day of my participation in the August More Text Challenge. For details, see:August is more challenging

channel

A channel is a communication mechanism in Go

The Go language concept: shared memory through communication, not shared memory through communication

Messages are sent and received through channels between goroutines

Channels are also typed, and a channel can only pass values of the same type

Channels are blocked by default unless its buffer size is specified when the channel is created

format

Var XXX chan Indicates the data type

Define different types of channels

ChB := make(chan int) fmt.Printf("%#v \n", chI) ChPerson := make(chan Person) fmt.Printf("%#v \n", chPerson)Copy the code

Channel operation

Ch0 := make(chan int) ch0 := make(chan int) ch0 := make(chan int) 2) // Channel on the left, data on the right, Indicates that data is sent to the channel ch0 < -10 CH0 < -20 // Close of the channel CLOSE (CH0) // Label of the receive variable of the channel = <- channel identifier //value := < -ch0 //value2 := < -ch0 / / FMT. Println (value) "the value:" in the passage, / / FMT Println (" the value: "in the passage, value2) / / used for... For v := range ch0 {if v == 0 {break} fmt.Println(" ch0: ", v)} for v := range ch0 {if v == 0 {break} fmt.Println(" ch0: ", v)}Copy the code

Define only send channels

Ch3 := make(chan< -int) fmt.Printf("%#v \n", ch3)Copy the code

Define receive channels only

Ch4 := make(<-chan int) fmt.Printf("%#v \n", ch4)Copy the code

Sending channel The use of receiving channels

Func sendCh0(ch chan < -int) {fmt.Println("sendCh0 sends values to the channel ") // Channel identifier of the channel <- Data of the channel type CH < -10} func receiveCh0(ch < -chan int) {// channel receiver variable tag = < -channel identifier value := < -ch fmt.Println("receiveCh0 ") ", value) } func main() { ch0 := make(chan int) go sendCh0(ch0) go receiveCh0(ch0) }Copy the code

Synchronous channel

func sendData(ch chan <- int) { for i := 0; i < 5; I ++ {FMT.Println(" to send data: ", I) ch < -i FMT.Println(" to send data: ", I) ch < -i FMT.Println(" to send data: ", I) ch ", I)}} func receiveData(ch < -chan int) {for v := range ch {fmt.Println(" received data ~~~~~~: ", v)}}Copy the code
Ch5 := make(chan int) //ch5 := make(chan int) 1) go sendData(ch5) go receiveData(ch5) time.Sleep(time.Second * 3)Copy the code

Asynchronous channel

Ch5 := make(chan int, ch5); 1) go sendData(ch5) go receiveData(ch5) time.Sleep(time.Second * 3)Copy the code

Precautions for synchronous and asynchronous channels

If it’s an unbuffered channel and it sends data to the channel and it’s not received, then the channel continues to be blocked until the data is received

A non-buffered channel, also known as a synchronous channel, can send data to a channel before sending data to it, but can’t receive data from it because the receiving channel is coroutine blocked

After you send data to the channel, you can receive data from the channel, but you can’t send data to the channel and that’s where the coroutine is blocked

If it’s a channel with a buffer and the buffer isn’t full, you can continue sending data into the channel, otherwise it’s blocked

There’s a buffer channel, also called an asynchronous channel where you can send data to the channel until the buffer is full, and the coroutine is blocked on the sending channel

If the buffer has data, data can be received from the channel until the buffer is empty and the coroutine where the receiving channel is blocked

Channel use in SELECT

When there are multiple channels to operate on

If a channel buffer is empty, receiving data from that channel will block

If a channel buffer is full, sending data to that channel will block

You can use the SELECT statement to solve the problem of multi-channel operations

ch6 := make(chan int, 1) ch7 := make(chan int, 1) for i := 0; i < 10; I ++ {select {case ch6 < -i: fmt.Println(", I) case v := < -ch6: fmt.Println(", I) case v := < -ch6: fmt.Println(", I) ", v) case ch7 < -i: fmt.Println(", I) case v := < -ch7: fmt.Println(", I)}}Copy the code

conclusion

Channels in Go give us a new communication mechanism in the concurrency model: shared memory via channel communication, rather than shared memory. This gives us more secure memory access and synchronization between coroutines. I seem to like this communication concept!!