Similar to blocking after sending on a channel, a go routine can block waiting to get a value from a channel, with nothing sent to it yet.
Blocking can be a bit confusing at first, but you can think of it like a transaction between two go routines (gophers). Whether a gopher is waiting for money or sending money, it will wait until the other partner in the transaction shows up.
Now that we have an idea on the different ways a go routine can block while communicating through a channel, lets discuss the two different types of channels: unbuffered, and buffered. Choosing what type of channel you use can change how your program behaves.
We will be looking at the buffered channels in next tutorial
One important factor to consider while using channels is deadlock. If a Goroutine is sending data on a channel, then it is expected that some other Goroutine should be receiving the data. If this does not happen, then the program will panic at runtime with Deadlock.
Similarly if a Goroutine is waiting to receive data from a channel, then some other Goroutine is expected to write data on that channel, else the program will panic.
In line no. 10 of the program above, a bidirectional channel chnl is created. It is passed as a parameter to the sendData Goroutine in line no. 11.
The sendData function converts this channel to a send only channel in line no. 5 in the parameter sendch chan<- int.
So now the channel is send only inside the sendData Goroutine but it's bidirectional in the main Goroutine. This program will print 10 as the output.
In the above statement ok is true if the value was received by a successful send operation to a channel.
If ok is false it means that we are reading from a closed channel. The value read from a closed channel will be the zero value of the channel's type.
For example if the channel is an int channel, then the value received from a closed channel will be 0.
In the program above, the producer Goroutine writes 0 to 9 to the chnl channel and then closes the channel.
The main function has an infinite for loop in line no.16 which checks whether the channel is closed using the variable ok in line no. 18.
If ok is false it means that the channel is closed and hence the loop is broken. Else the received value and the value of ok is printed.
Hopefully, this article helped get a good grasp of goroutines, goroutine communication and how they are scheduled. I will be writing a follow-up article on the inner workings of channels to better understand how to use them co-ordinate your goroutines better.
Till then, try and play around with goroutines and explore different result, or you could even try and explore parallelism by setting the GOMAXPROCS to the number of cores available in your CPU (Caution advised).