Quantifier menentukan berapa kali hal yang tepat di depannya boleh berulang. Tanpa quantifier, tiap bagian pola cocok tepat satu kali. Mirip aturan di form PO Bu Ratna: "nastar minimal 1 toples", "kartu ucapan boleh ada, boleh gak", "maksimal 5 toples per orang". Aturannya gak menyebut barangnya, cuma jumlahnya, dan berlaku untuk barang yang disebut tepat sebelumnya.
🧪 Tebakan cepat: di baris pertama chat ada tiga teks tebal ala WhatsApp:
*Nastar*,*Kastengel*,*Putri Salju*.chat.match(/\*.+\*/g)mengambil*Nastar*saja, ketiganya terpisah, atau satu potongan panjang? Tebak dulu, jawabannya ada di bagian "Greedy dan lazy".
Quantifier mengulang satu hal di depannya
| Quantifier | Artinya | Contoh dari chat |
|---|---|---|
? |
0 atau 1 kali (opsional) | -? tanda strip boleh ada |
* |
0 kali atau lebih | 08\d* |
+ |
1 kali atau lebih | [\d.]+ |
{4} |
tepat 4 kali | PO-\d{4} |
{8,11} |
8 sampai 11 kali | 08\d{8,11} |
{2,} |
minimal 2 kali | \d{2,} |
console.log(chat.match(/Rp[\d.]/g)); // ['Rp8', 'Rp1', 'Rp1']
console.log(chat.match(/Rp[\d.]+/g)); // ['Rp85.000', 'Rp165.000', 'Rp170.000']
console.log(chat.match(/\d+rb/g)); // ['90rb', '255rb']
Rp[\d.]tanpa quantifier:Rplalu satu angka atau titik. Hasilnya terpotong:Rp8.Rp[\d.]+:+mengulang class[\d.]sebanyak mungkin, jadi harganya utuh.\d+rb: angka satu atau lebih, lalu tulisanrb. Harga gaya singkat ikut ketemu.- Quantifier cuma mengulang satu hal tepat di depannya.
/Rp+/mengulang hurufpsaja, bukanRp.
?, *, dan + di nomor HP
console.log(chat.match(/08\d+/g)); // ['0812', '081298765432']
console.log(chat.match(/08\d*/g)); // ['08', '08', '0812', '08', '08', '08', '081298765432', '08']
console.log(chat.match(/08\d{2}-?\d{4}-?\d{4}/g)); // ['0812-3456-7890', '081298765432']
08\d+minta minimal satu angka setelah08. Di nomor Dina, angkanya berhenti di tanda strip, jadi cuma0812.08\d*boleh nol angka. Jam08.15di tiap baris ikut ketemu sebagai08, karena*sudah puas dengan nol angka.-?artinya tanda strip boleh ada, boleh gak. Satu pola menangkap0812-3456-7890dan081298765432.
Jumlah pasti: {n}, {n,m}, {n,}
console.log(chat.match(/08\d{8,11}/g)); // ['081298765432']
console.log(chat.match(/\d{10,13}/g)); // ['1234567890', '081298765432']
console.log("aabbb".match(/ab{2,3}/)[0]); // 'abbb'
08\d{8,11}:08lalu 8 sampai 11 angka, jadi nomor 10 sampai 13 digit tanpa tanda strip.\d{10,13}juga menangkap nomor rekening1234567890, karena polanya cuma menghitung angka. Cara membedakannya ada di pelajaran Anchors.{n,}artinya minimal n kali, tanpa batas atas.{,3}gak ada di JavaScript:/a{,3}/malah mencari tulisana{,3}apa adanya.ab{2,3}diaabbb: boleh 2 atau 3 huruf b, dan quantifier mengambil sebanyak mungkin, jadi hasilnyaabbb.
Greedy dan lazy
Quantifier itu greedy (rakus): dia mengambil sebanyak mungkin dulu, baru mundur sedikit-sedikit kalau sisa pola gak cocok.
console.log(chat.match(/\*.+\*/g)); // ['*Nastar* Rp85.000/toples, *Kastengel* 90rb, *Putri Salju*']
console.log(chat.match(/\*.+?\*/g)); // ['*Nastar*', '*Kastengel*', '*Putri Salju*']
console.log("aXXbXX".match(/X+/g)); // ['XX', 'XX']
console.log("aXXbXX".match(/X+?/g)); // ['X', 'X', 'X', 'X']
\*.+\*:.+makan sampai ujung baris, lalu mundur sampai ketemu*terakhir. Hasilnya satu potongan panjang dari*NastarsampaiSalju*. Itu jawaban tebakannya.?setelah quantifier membuatnya lazy (hemat): ambil sesedikit mungkin.\*.+?\*berhenti di*berikutnya, jadi tiap teks tebal terpisah.X+?cukup dengan satuX, jadi denganghasilnya empatXsatu-satu.- Sama di HTML:
"<b>tebal</b> dan <i>miring</i>".match(/<.+>/)[0]mengambil seluruh teks, sedangkan/<.+?>/gmemberi['<b>', '</b>', '<i>', '</i>'].
⚠️ Jebakan yang sering ketemu
*cocok dengan teks kosong./\d*/.test("halo")hasilnyatrue, karena nol angka juga dihitung cocok, dan"halo".match(/\d*/)memberi['']di index 0. Kalau minimal harus ada satu, pakai+.- Lupa quantifier cuma mengulang satu hal.
/ha+/cocok denganhaaa, bukanhahaha. Mengulang beberapa karakter sekaligus butuh grup, dibahas di pelajaran Groups. - Greedy di teks yang berulang.
.+di antara dua pembatas sering makan terlalu banyak. Pakai lazy.+?, atau class yang menolak pembatasnya:\*[^*]+\*. - Quantifier tanpa apa-apa di depannya.
/*Nastar*/ditolak:Invalid regular expression: /*Nastar*/: Nothing to repeat. Mau mencari bintangnya?\*.
TL;DR: Quantifier mengatur berapa kali hal tepat di depannya berulang: ? 0 atau 1, * 0 atau lebih, + 1 atau lebih, {n} tepat n, {n,m} antara n dan m, {n,} minimal n. Quantifier itu greedy: "aabbb".match(/ab{2,3}/)[0] memberi abbb, dan \*.+\* menelan dari bintang pertama sampai terakhir. Tambah ? untuk lazy: \*.+?\* mengambil tiap teks tebal, X+? satu X per hasil. * bisa cocok dengan nol karakter, jadi test() dengan \d* selalu true.