One of Go’s mottos is:

Share memory by communicating, don’t communicate by sharing memory

Here is a mini channel example

Go:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
package main

import "fmt"

func sendMessage(messages chan<- string) {
	messages <- "ping"
}

func main() {
	messages := make(chan string)
	go sendMessage(messages)
	msg := <-messages
	fmt.Println(msg)
}

What’s happening here is:

By default a channel is unbuffered, meaning it is synchronized. This means that a value must be received from the channel at the same time as it’s being sent. We can verify this by calling sendMessage() directly instead of as a goroutine. If we do that, the program crashes!

Channels with buffering

It’s also possible to buffer a channel with multiple values. We do this by adding a number to the make call when we create a channel.

Go:
1
2
3
4
5
6
7
8
9
10
11
package main

import "fmt"

func main() {
	messages := make(chan int, 2)
	messages <- 1
	messages <- 2
	fmt.Println(<-messages)
	fmt.Println(<-messages)
}