पाठ 4 / 25

Unbuffered vs Buffered Channels

When sends and receives block.

Blocking semantics

make(chan T) creates an unbuffered channel: a send blocks until a receiver takes the value, and a receive blocks until a sender provides one, so the two goroutines synchronise at the hand-off. make(chan T, n) creates a buffered channel with capacity n: a send blocks only when the buffer is full, and a receive blocks only when it is empty. len(ch) and cap(ch) report the number of queued items and the capacity, but len is stale as soon as you read it, so do not use it for coordination. Buffers smooth out bursts and decouple producer and consumer speeds; they do not fix a design where the consumer is permanently slower. A send with no possible receiver blocks forever; if every goroutine is blocked like that, the runtime aborts with fatal error: all goroutines are asleep - deadlock!

Typed pipes between goroutines

Channels move values between goroutines and synchronise them; their blocking rules are the heart of Go concurrency.

Three ideas: buffering and blocking, closing and ranging, and channel direction in APIs.
Figure 2.1: a sender, a channel and a receiver.

Unbuffered hand-off vs buffered queue

The unbuffered send waits for the receiver; the buffered sends do not.

package main

import "fmt"

func main() {
	// Unbuffered: the send completes only when main receives.
	done := make(chan string)
	go func() { done <- "work finished" }()
	fmt.Println(<-done)

	// Buffered with capacity 2: two sends succeed without a receiver.
	queue := make(chan int, 2)
	queue <- 1
	queue <- 2
	fmt.Println(len(queue), cap(queue)) // 2 2
	// queue <- 3 would block here: buffer full and nobody receiving.
	fmt.Println(<-queue, <-queue)       // FIFO order: 1 2
}

Choose buffer sizes deliberately

Default to unbuffered or a buffer of 1. A larger buffer should have a reason you can state, such as "at most N in-flight jobs"; a big buffer chosen to make a deadlock disappear usually just postpones it.

त्वरित जाँच: When does a send on a buffered channel with capacity 3 block?

  • Always, until a receiver is ready
  • When the buffer already holds 3 values
  • Never, buffered sends are non-blocking
  • Only after the channel is closed
Answer

When the buffer already holds 3 values — A buffered send blocks only when the buffer is full.