← Kembali ke kursus
Pelajaran kursus · Go
Pelajaran 29

Channel - Range & Close

Tutup channel dan susuri isinya sampai habis.

Pahami konsepnya

close(ch) menutup sebuah channel: tidak ada pengiriman lagi yang diterima (mengirim ke channel tertutup membuat program panic), tetapi penerimaan tetap boleh dan menghabiskan sisa nilai di buffer.

Setelah semua nilai terkuras, penerimaan berikutnya langsung mengembalikan nilai nol. Bentuk v, ok := <-ch membedakan keadaan: ok true berarti nilai asli, ok false berarti channel sudah tertutup dan kosong.

Yang paling sering dipakai: for v := range ch — loop menerima terus sampai channel ditutup, lalu selesai dengan rapi. Konvensinya penting: channel ditutup oleh PENGIRIM, tidak pernah penerima, dan menutup memang tujuannya memberi tahu "tidak ada data lagi". Menerima dari channel nil juga mengembalikan nilai nol tanpa menunggu — kadang berguna sebagai channel mati.

Coba contoh kode

package main

import "fmt"

func kirim(ch chan int) {
    for i := 1; i <= 3; i++ {
        ch <- i
    }
    close(ch) // pengirim memberi tahu: data habis
}

func main() {
    ch := make(chan int)
    go kirim(ch)

    for v := range ch {
        fmt.Println(v) // 1, 2, 3, lalu loop berhenti sendiri
    }
}

range menerima 1, 2, 3 lalu berhenti dengan sendirinya begitu close terdeteksi — tidak perlu tahu berapa banyak data yang akan datang. Coba kirim setelah close: ch <- 4 membuat panic. Pola kirim-N-lalu-close ini adalah bentuk paling umum channel di program nyata.

Memeriksa status channel

func main() {
    ch := make(chan int, 2)
    ch <- 10
    close(ch)

    v, ok := <-ch
    fmt.Println(v, ok) // 10 true — sisa buffer

    v, ok = <-ch
    fmt.Println(v, ok) // 0 false — sudah kering
}

Penerimaan pertama masih mendapat nilai 10 dari sisa buffer dengan ok true. Penerimaan kedua mendapat 0 dan ok false — sinyal resmi bahwa channel tertutup dan kosong. Bentuk dua nilai ini adalah cara eksplisit memeriksa bila range tidak memungkinkan.

Latihan singkat

Uji: goroutine mengirim lima fibonacci pertama lalu menutup channel; main menerimanya dengan for range — harus `1 1 2 3 5` (satu per baris).