Concurrent programming in Go language_Channel

Introduction to channel

The concurrency model of Go language, CSP (Communicating Sequential Processes), advocates sharing memory through communication instead of sharing memory.

Although you can use shared memory for data exchange, shared memory is prone to race conditions in different goroutines. In order to ensure the correctness of data exchange, a mutex must be used to lock the memory, which is bound to cause performance problems.

  • channel: It is the communication mechanism in Go language that sends a goroutine a specific value to another goroutine.
    Channel in Go language is a special type. A channel is a queue that always follows the First In First Out (First In First Out) rule to ensure the order of sending and receiving data. Each channel is a specific type of conduit, that is, when you declare the channel, you need to specify the element type for it.

Use of channel

type of channel

  • Channel is a reference type. The format for declaring a channel is as follows:
var 变量 chan 元素类型
-------------------------
    var ch1 chan int   // 声明一个传递整型的通道
    var ch2 chan bool  // 声明一个传递布尔型的通道
    var ch3 chan []int // 声明一个传递int切片的通道

Create channel

Since the channel is a reference type, the value of the channel defaults to nil

	var ch1 chan int
	fmt.Println(ch1)//<nil>

After the channel is declared, it needs to be initialized with the make function before it can be used.
The syntax of make to initialize the channel is:

    make(chan 元素类型, [缓冲大小])

Operation channel

Channel has three operations: both 发送,接收,关闭
sending and receiving are used:<-

	ch1 := make(chan int)
	ch1 <- 10//将10发送到ch1中
	x :=<-ch1 //从ch1接收值并赋给x

shut down:

close(ch1)

Note: It is not necessary to close the channel. The channel needs to be closed only when the receiver goroutine is notified that all the data has been sent. The channel can be garbage collected.
Sending values ​​or closing operations to a closed channel will cause panic.
The received value of a closed channel can be taken to the value until the channel is empty, and when the channel has no value, the value obtained again can only be the zero value of the corresponding type.

Unbuffered channel

Insert picture description here
Unbuffered channels are also called blocked channels:

	ch1 := make(chan int)
	ch1 <- 10//将10发送到ch1中

By ch1 := make(chan int)creating an unbuffered channel, the unbuffered channel can only send values ​​when the receiver exists, otherwise a deadlock error will occur.

fatal error: all goroutines are asleep - deadlock!
goroutine 1 [chan send]:
main.main()

There are two solutions:

  1. Start a goroutine to receive
func recvdata(c chan int)  {
    
    
	data :=<-c
	fmt.Println("接收成功data",data)
}
func main() {
    
    
	//var ch1 chan int
	//fmt.Println(ch1)
	ch1 := make(chan int)
	go recvdata(ch1)//启动goroutine接收通道里面的值
	ch1<-10//发送10
	fmt.Println("发送成功")
}

同步通道: The sending operation on the unbuffered channel will block until another goroutine performs the receiving operation on the channel, then the value can be sent successfully, and the two goroutines will continue to execute. On the contrary, if the receiving operation is performed first, the goroutine of the receiver will block until another goroutine sends a value on the channel.
Using unbuffered channels for communication will result in synchronization of the sending and receiving goroutines. Therefore, unbuffered channels are also called synchronous channels.

Buffer channel

A buffered channel is also a solution to the problem of an unbuffered channel.
Insert picture description here
As long as the capacity of the channel is greater than zero, then the channel is a buffered channel. The capacity of the channel indicates the number of elements that can be stored in the channel.
Create a buffered channel:

  ch := make(chan int, 1) // 创建一个容量为1的有缓冲区通道

There will be no deadlock situation in this way. And this data also exists in this channel for buffering.

One-way channel

A one-way channel is provided in the Go language to restrict data to only be sent or received

  1.chan<- int是一个只能发送的通道,可以发送但是不能接收;
  out chan <-int
  2.<-chan int是一个只能接收的通道,可以接收但是不能发送。
  in <-chan int

A two-way channel can be changed to one-way, but a one-way channel cannot be changed to two-way.

Guess you like

Origin blog.csdn.net/H1517043456/article/details/112986275