Concurrency: Goroutines and Channels
Harry
· 14 Sep 2026
· 1 views
Advertisement
Goroutines
A goroutine is a function running concurrently, started by putting go before a call. Goroutines are extremely lightweight – you can run thousands – because the Go runtime multiplexes them onto a few OS threads:
go doWork() // runs concurrently; main continues
go fmt.Println("hi") // starts another goroutine
Channels connect goroutines
Go's motto is “do not communicate by sharing memory; share memory by communicating.” A channel is a typed pipe that goroutines use to send and receive values safely:
ch := make(chan int)
go func() {
ch <- 42 // send
}()
result := <-ch // receive (blocks until a value arrives)
Waiting for many goroutines
A sync.WaitGroup lets the main function wait for a set of goroutines to finish:
var wg sync.WaitGroup
for _, url := range urls {
wg.Add(1)
go func(u string) {
defer wg.Done()
fetch(u)
}(url)
}
wg.Wait() // block until all are done
select
select waits on multiple channel operations at once – the basis of timeouts and coordinating several channels:
select {
case msg := <-ch:
fmt.Println(msg)
case <-time.After(time.Second):
fmt.Println("timed out")
}
Key points
- Start concurrent work with
go; goroutines are cheap and numerous. - Channels safely pass typed values between goroutines – share by communicating.
- Use a
WaitGroupto wait for multiple goroutines to complete. selectwaits on several channels at once, enabling timeouts.