What does this print? (request/response over a channel of channels)
Question 213HardGo 1.22 to 1.25
package main
import "fmt"
func main() {
reqs := make(chan chan int)
go func() {
n := 0
for reply := range reqs {
n++
reply <- n
}
}()
for range 3 {
r := make(chan int)
reqs <- r
fmt.Print(<-r, " ")
}
close(reqs)
}
Output: 1 2 3 . It is deterministic.
This is the request/response via channel-of-channels pattern. The server goroutine owns n (so no mutex is needed), and each request brings its own reply channel. Everything is unbuffered, so each iteration completes the full round trip before the next starts. This is how you build an "actor" or state-owning goroutine: serialize access to state by giving it to a single goroutine. It's a good lead-in to discussing its costs: every access pays two channel operations and a context switch, so a mutex is usually faster for simple state.
More on Channels & select
- Q211Does an unbuffered channel give a happens-before guarantee? What does the memory model say about channels?
- Q212Implement a generic "first response wins" (hedged request / race) function.
- Q214How would you implement rate limiting using channels?
- Q215Can you compare channels with
==, use them as map keys, and send channels over channels? - Q216How do you gracefully shut down a service that uses channels and goroutines?
- Q217What does this print? (
breakinsideselectinsidefor)