Array Punya Kotak Perkakas
Array JavaScript membawa banyak method bawaan. Sebagian besar hal yang biasanya kamu tulis dengan loop for, seperti mengubah nilai, memilih sebagian, atau menjumlahkannya, punya method yang melakukannya dalam satu baris, lebih enak dibaca, dan mudah digabungkan dengan method lain.
Bekal awalnya tiga method: map, filter, dan reduce. Kuasai ketiganya beserta beberapa kerabatnya, dan kode yang penuh loop akan menyusut menjadi sesuatu yang bisa kamu pahami sekilas.
Setiap method menerima callback dan mengembalikan sesuatu. Tidak ada satu pun yang mengubah nums. Ini pola yang sebaiknya kamu pahami sejak awal.
map: Mengubah Setiap Elemen
map menerima sebuah fungsi dan memanggilnya pada setiap elemen, lalu mengumpulkan nilai kembaliannya ke array baru dengan panjang yang sama. Pakai saat kamu ingin "satu output untuk setiap input".
Callback juga menerima index sebagai argumen kedua kalau kamu membutuhkannya: arr.map((item, i) => ...). Abaikan saja kalau tidak perlu.
Satu kesalahan umum: memakai map padahal kamu tidak butuh array yang dikembalikan. Kalau kamu hanya ingin mencetak setiap item atau menyimpannya ke database, itu tugas forEach atau loop biasa.
filter: Menyimpan yang Cocok
filter memanggil sebuah predikat, yaitu fungsi yang mengembalikan true atau false, pada setiap elemen dan menyimpan elemen yang hasilnya truthy. Array barunya punya panjang yang sama atau lebih pendek.
map dan filter mudah dirangkai. Baca rangkaiannya dari kiri ke kanan seperti sebuah pipeline:
Filter dulu, baru map. Dengan begitu map hanya berjalan pada elemen yang lolos.
reduce: Meringkas Array Menjadi Satu Nilai
reduce adalah yang paling umum di antara ketiganya. Kamu memberinya fungsi reducer (accumulator, item) => newAccumulator dan nilai awal. Method ini menelusuri array, memberikan setiap item ke reducer bersama akumulator sejauh ini, lalu mengembalikan nilai akhir akumulatornya.
Hasilnya tidak harus berupa angka. Bisa berupa objek, array lain, string, apa pun yang kamu bangun:
Selalu berikan nilai awal (argumen kedua). Tanpa nilai awal, reduce memakai elemen pertama sebagai akumulator awal, yang gagal pada array kosong dan sering kali memang bukan yang kamu inginkan.
reduce sangat kuat, tetapi bisa sulit dibaca kalau logikanya rumit. Kalau reducer kamu lebih dari beberapa baris, loop for...of biasa sering kali lebih jelas.
forEach: Efek Samping, Tanpa Nilai Kembalian
forEach mirip map tetapi tanpa array yang dikembalikan. Method ini ada untuk saat kamu ingin melakukan sesuatu pada setiap item, seperti mencetaknya, memanggil API, atau memperbarui DOM, dan tidak butuh koleksi baru.
Dua hal yang perlu kamu ketahui:
forEachmengembalikanundefined. Kamu tidak bisa merangkai.map()setelahnya.- Kamu tidak bisa keluar lebih awal dari
forEachdenganbreak. Kalau butuh berhenti lebih awal, pakaifor...ofatausome/every.
Kalau kamu mendapati dirimu menulis arr.forEach(x => results.push(transform(x))), itu sebenarnya map.
find dan findIndex: Cukup Satu Saja
find mengembalikan elemen pertama yang cocok dengan predikat, atau undefined kalau tidak ada yang cocok. findIndex mengembalikan index-nya (atau -1).
find berhenti di kecocokan pertama. Jangan pakai filter(...)[0], karena cara itu memindai seluruh array hanya untuk membuang sisanya.
some dan every: Pertanyaan Boolean
some mengembalikan true kalau setidaknya satu elemen lolos pengujian. every mengembalikan true hanya kalau semuanya lolos.
Keduanya melakukan short-circuit: some berhenti di true pertama, every berhenti di false pertama. Keduanya alat yang tepat untuk pertanyaan "apakah ada yang…" dan "apakah semuanya…".
slice vs splice: Menyalin vs Memotong
Keduanya terdengar mirip, tetapi cara kerjanya sangat berbeda.
slice(start, end) mengembalikan salinan dangkal dari sebagian array. Method ini tidak mengubah apa pun. end tidak ikut disertakan; hilangkan saja kalau ingin sampai ke akhir array.
splice(start, deleteCount, ...items) mengubah array langsung di tempat. Method ini menghapus deleteCount elemen mulai dari start, bisa juga menyisipkan elemen baru, lalu mengembalikan elemen yang dihapus.
Cara mengingatnya: slice itu aman (menyalin), splice membedah array langsung di tempat.
Mengubah Array Asli vs Tidak
Perbedaan ini penting. Kode yang tanpa sengaja mengubah array yang dipakai bersama adalah salah satu bug yang paling menyebalkan untuk dilacak.
Mengubah array asli (memodifikasi aslinya, biasanya mengembalikan sesuatu yang lain):
push,pop,shift,unshiftsplice,sort,reversefill,copyWithin
Tidak mengubah array asli (mengembalikan array atau nilai baru, aslinya tidak tersentuh):
map,filter,slice,concatflat,flatMapfind,findIndex,some,every,includes,indexOfreduce,reduceRight
Dua yang perlu diwaspadai adalah sort dan reverse: keduanya terlihat tidak berbahaya tetapi diam-diam mengubah array. Kalau kamu butuh salinan yang sudah diurutkan, pakai slice dulu:
JS modern juga punya kembaran yang tidak mengubah array asli: toSorted, toReversed, toSpliced, dan with. Semuanya mengembalikan array baru dan membiarkan aslinya. Didukung di semua runtime saat ini, jadi pakai saja kalau tersedia.
flat dan flatMap
flat meratakan array bersarang satu tingkat (atau lebih, dengan argumen kedalaman). flatMap adalah map yang diikuti flat satu tingkat, berguna saat setiap item menghasilkan nol output atau lebih.
flatMap adalah cara rapi untuk "memekarkan" item, satu input menjadi banyak output, tanpa langkah flat() tambahan.
Menggabungkan Semuanya
Contoh kecil yang realistis. Dari daftar pesanan, hitung total pendapatan dari pesanan yang selesai dengan nilai di atas $50:
Tiga method, satu pipeline, tanpa urusan pencatatan loop. Setiap langkah menjelaskan apa yang dilakukannya. Kamu bisa menggabungkan kedua panggilan filter, tetapi memisahkannya tetap enak dibaca dan kadang membantu saat kamu sedang debug.
Berikutnya: Map dan Set
Array menangani urutan data dengan baik, tetapi kurang praktis saat kamu butuh pencarian cepat berdasarkan key atau koleksi nilai yang unik. JavaScript punya dua struktur data bawaan untuk tugas-tugas itu, yaitu Map dan Set, dan keduanya dibahas di halaman berikutnya.
Pertanyaan yang sering diajukan
Apa bedanya map, filter, dan reduce di JavaScript?
map mengubah setiap elemen dan mengembalikan array baru dengan panjang yang sama. filter hanya menyimpan elemen yang lolos pengujian dan mengembalikan array baru (biasanya lebih pendek). reduce menelusuri array dan meringkasnya menjadi satu nilai: jumlah, objek, array lain, atau apa pun yang kamu bangun.
Apa bedanya forEach dan map?
forEach menjalankan fungsi untuk setiap elemen dan mengembalikan undefined, jadi gunanya untuk efek samping. map menjalankan fungsi untuk setiap elemen dan mengembalikan array baru berisi hasilnya. Kalau kamu ingin array yang sudah diubah, pakai map. Kalau kamu hanya ingin melakukan sesuatu pada tiap elemen dan tidak butuh hasilnya, pakai forEach (atau loop for...of).
Method array mana yang mengubah array asli?
Yang mengubah array asli adalah push, pop, shift, unshift, splice, sort, reverse, fill, dan copyWithin. Sisanya, yaitu map, filter, slice, concat, flat, flatMap, find, some, every, reduce, membiarkan array asli dan mengembalikan nilai baru.
Kapan sebaiknya memakai slice dan kapan splice?
slice(start, end) mengembalikan salinan dangkal dari sebagian array dan tidak menyentuh array aslinya. splice(start, deleteCount, ...items) mengubah array: method ini menghapus dan/atau menyisipkan elemen langsung di tempat dan mengembalikan elemen yang dihapus. Cara mengingatnya: slice itu aman, splice membedah array.