Mendeklarasikan array
Tipe array ditulis [N]T: panjang, lalu tipe elemen. Panjangnya sudah tetap saat kompilasi dan menjadi bagian dari tipe.
Output:
[90 0 0 0 75] 5
Tue
[5]int [2 3 5 7 11]
["" "b" "" "d" ""]
Array selalu terinisialisasi penuh. Elemen yang tidak kamu isi berisi zero value dari tipe elemennya: 0, "", false, nil.
Indeks dan batas
Indeks berjalan dari 0 sampai len(a)-1. Indeks konstanta di luar jangkauan adalah error kompilasi. Indeks berupa variabel yang di luar jangkauan akan panic saat program berjalan.
var a [3]int
a[5] = 1 // compile error: invalid argument: index 5 out of bounds [0:3]
i := 5
a[i] = 1 // panic: runtime error: index out of range [5] with length 3
Menelusuri array
for i, v := range a mengunjungi setiap elemen secara berurutan. v adalah salinan elemen, jadi mengubah v tidak mengubah array. Ubah lewat indeksnya.
Ada satu kehalusan lagi yang khusus untuk array: range atas nilai array mengevaluasi salinan array di awal. Kalau badan perulangan mengubah elemen berikutnya, v tetap menunjukkan nilai lama. Melakukan range atas &a atau a[:] menghindari salinan itu.
Array adalah nilai
Inilah perbedaan utama dengan array di C, Java, atau JavaScript. Meng-assign array menyalin setiap elemennya. Mengirim array ke fungsi juga menyalinnya.
Output:
[1 2 3] [99 2 3]
[1 2 3]
[0 2 3]
Menyalin itu murah untuk array kecil dan mahal untuk array besar: mengirim [1_000_000]int sebagai nilai menyalin delapan megabyte. Kirim pointer (*[N]T) atau slice (a[:]) kalau array-nya besar atau fungsinya perlu mengubah isinya. Mengakses indeks lewat pointer array tidak butuh * eksplisit: a[0] bisa dipakai pada *[3]int.
Membandingkan array dan memakainya sebagai key map
Array berisi elemen yang bisa dibandingkan mendukung == dan !=. Dua array sama jika setiap elemennya sama. Itu juga membuat array sah sebagai key map, sesuatu yang tidak bisa dilakukan slice.
Array dengan panjang berbeda adalah tipe yang berbeda dan sama sekali tidak bisa dibandingkan: [3]int{} == [4]int{} tidak bisa dikompilasi (mismatched types [3]int and [4]int).
Array multidimensi
Array berisi array memberimu grid berukuran tetap. Seluruh grid adalah satu blok memori yang bersambung.
row[:] mengubah baris [3]rune menjadi slice []rune, yang diterima oleh string().
Array vs slice
Array [N]T | Slice []T | |
|---|---|---|
| Panjang | tetap, bagian dari tipe | berubah dengan append |
| Assignment dan pengiriman ke fungsi | menyalin semua elemen | menyalin header kecil, elemennya dipakai bersama |
| Zero value | N elemen bernilai nol | nil, panjang 0 |
== | ya, elemen demi elemen | hanya terhadap nil |
| Key map | ya | tidak |
| Kegunaan umum | data berukuran tetap: hash, koordinat, buffer | hampir semua hal lainnya |
Dalam praktik, kamu akan lebih sering menemui array di beberapa tempat saja: sha256.Sum256 mengembalikan [32]byte, tabel lookup yang ukurannya tidak pernah berubah, dan sebagai tempat penyimpanan di balik sebuah slice. Memotong array dengan a[:] atau a[1:3] membuat slice yang memakai memori yang sama; halaman slice menjelaskan arti berbagi memori itu.
Konversi antara array dan slice
Mengonversi slice ke array (Go 1.20) atau ke pointer array (Go 1.17) akan panic jika slice lebih pendek dari panjang array: panic: runtime error: cannot convert slice with length 2 to array or pointer to array with length 3.
Kesalahan umum
- Berharap fungsi mengubah argumen array. Fungsi itu menerima salinan. Kirim
*[N]Tatau slice. - Memakai array di tempat yang butuh slice.
[]int{1, 2}adalah slice,[2]int{1, 2}adalah array. Fungsi yang menerima[]inttidak akan menerima[2]int; kirima[:]. - Array besar di perulangan range.
for _, v := range bigArraymenyalin seluruh array lebih dulu. Lakukan range atas&bigArrayatau sebuah slice.
Pertanyaan yang sering diajukan
Bagaimana cara mendeklarasikan array di Go?
Tulis panjangnya di dalam kurung siku sebelum tipe elemen: var a [5]int membuat lima angka nol. Dengan nilai: a := [3]string{"x", "y", "z"}. Pakai [...] agar compiler yang menghitung: a := [...]int{1, 2, 3} bertipe [3]int.
Apa bedanya array dan slice di Go?
Array punya panjang tetap yang menjadi bagian dari tipenya ([3]int dan [4]int adalah tipe yang berbeda) dan disalin saat di-assign atau dikirim ke fungsi. Slice ([]int) adalah tampilan ke sebuah array di baliknya, dengan panjang yang bisa berubah lewat append, dan menyalin slice hanya menyalin tampilannya, bukan elemennya. Kebanyakan kode Go memakai slice.
Bagaimana cara mengetahui panjang array di Go?
Pakai fungsi bawaan len(a). Untuk array, nilainya adalah konstanta yang sudah diketahui saat kompilasi, jadi kamu bisa memakainya di ekspresi konstanta. cap(a) mengembalikan angka yang sama.
Apakah array bisa dibandingkan di Go?
Bisa, dengan == dan !=, asalkan tipe elemennya bisa dibandingkan. Dua array sama jika semua elemennya sama. Array juga bisa dipakai sebagai key map. Slice tidak bisa dibandingkan dengan == (kecuali dengan nil); untuk slice, pakai slices.Equal.