Masukkan Password
31 Pola Rest & Parameter Rest
Kalau di lecture sebelumnya kita belajar Spread Operator (...), sekarang kita belajar pasangan konsepnya, yaitu Rest Pattern dan Rest Parameter.
Keduanya memang agak membingungkan karena sama-sama menggunakan tiga titik ... seperti spread. Bedanya bukan pada simbolnya, tetapi pada konteks dan arah kerjanya.
Kalau mau dibuat sesederhana mungkin:
Spread = membongkar / menyebarkan isi.
Rest = mengumpulkan / membungkus sisa isi.

1. Gambaran besar dulu
Kita sudah punya:
...
Tiga titik ini bisa memiliki dua peran:
...
│
┌──────┴──────┐
│ │
SPREAD REST
│ │
membongkar mengumpulkan
menyebarkan sisa nilai
Contoh:
[...users]
→ Spread
Sedangkan:
const [first, ...rest] = users;
→ Rest Pattern
Dan:
function add(...numbers) {}
→ Rest Parameter
2. Apa itu Rest Pattern?
Rest Pattern digunakan ketika kita melakukan destructuring, lalu ingin mengumpulkan sisa nilai ke dalam sebuah array.
Contoh:
const numbers = [1, 2, 3, 4, 5];
const [a, b, ...rest] = numbers;
Sekarang hasilnya:
a → 1
b → 2
rest → [3, 4, 5]
Jadi rest bukan berisi:
3
tetapi:
[3, 4, 5]
Karena ...rest mengatakan:
“Ambil semua nilai yang masih tersisa dan kumpulkan menjadi satu array.”
3. Kenapa disebut “Rest”?
Kata rest secara sederhana berarti:
sisanya
Misalnya ada:
1 2 3 4 5
Kita mengambil:
1 → a
2 → b
Lalu apa yang tersisa?
3 4 5
Nah, bagian yang tersisa itulah yang dikumpulkan oleh:
...rest
Visualnya:
numbers
┌─────────────────────┐
│ 1 │ 2 │ 3 │ 4 │ 5 │
└─────────────────────┘
↓ ↓ └────┬────┘
a b rest
↓
[3, 4, 5]
Ini adalah inti dari Rest Pattern.
4. Bedah kode satu per satu
Kode:
const [a, b, ...rest] = [1, 2, 3, 4, 5];
Mari kita baca dari kiri.
Variable pertama
a
mendapat:
1
Variable kedua
b
mendapat:
2
Rest Pattern
...rest
mengambil semua sisanya:
3
4
5
dan mengemasnya menjadi:
[3, 4, 5]
Jadi:
console.log(a);
// 1
console.log(b);
// 2
console.log(rest);
// [3, 4, 5]
5. Tanpa Rest Pattern
Sekarang bandingkan:
const [a, b, rest] = [1, 2, 3, 4, 5];
Hasil:
a → 1
b → 2
rest → 3
Yang terjadi pada 4 dan 5?
Tidak diambil.
1 → a
2 → b
3 → rest
4 → ❌
5 → ❌
Karena destructuring biasa bekerja berdasarkan posisi.
Tetapi:
const [a, b, ...rest] = [1, 2, 3, 4, 5];
berarti:
1 → a
2 → b
3,4,5 → rest
6. Rest Pattern = “ambil sisanya”
Ini mental model yang sangat bagus:
Array:
[ 1, 2, 3, 4, 5 ]
Destructuring:
↓ ↓
a b
Rest:
↓──────────↓
3 4 5
↓
[3, 4, 5]
Jadi:
Rest Pattern menangkap semua bagian yang belum diambil oleh destructuring.
7. Rest Pattern harus berada di bagian akhir
Ini aturan yang sangat penting.
Contoh yang benar:
const [a, b, ...rest] = [1, 2, 3, 4, 5];
Tetapi ini tidak valid:
const [...rest, a] = [1, 2, 3, 4, 5];
Kenapa?
Karena JavaScript tidak tahu:
“Berapa banyak yang harus dimasukkan ke
rest, dan mana yang harus diberikan kea?”
Misalnya:
1 2 3 4 5
Apakah:
rest = [1,2,3,4]
a = 5
atau:
rest = [1,2,3]
a = 4
atau:
rest = [1,2]
a = 3
Tidak ada cara yang jelas.
Karena itu rest pattern harus menjadi bagian terakhir.
const [a, b, ...rest] = numbers;
8. Rest Pattern bukan cuma untuk array
Rest Pattern juga bisa digunakan pada object destructuring.
Misalnya:
const user = {
name: "John",
age: 28,
gender: "male",
city: "Jakarta"
};
Kita bisa:
const { name, ...rest } = user;
Hasil:
name → "John"
rest →
{
age: 28,
gender: "male",
city: "Jakarta"
}
Perhatikan sesuatu yang menarik:
Untuk array, rest menghasilkan array.
const [first, ...rest] = numbers;
→
rest = [2, 3, 4, 5]
Untuk object, rest menghasilkan object.
const { name, ...rest } = user;
→
rest = {
age: 28,
gender: "male",
city: "Jakarta"
}
9. Rest Pattern pada Object
Misalnya:
const employee = {
name: "John",
age: 28,
company: "Google",
salary: 1200
};
Kemudian:
const { name, ...details } = employee;
Hasil:
name
↓
"John"
details
↓
{
age: 28,
company: "Google",
salary: 1200
}
Jadi ...details mengumpulkan semua properties yang belum diambil.
10. Sekarang kita masuk ke Rest Parameter
Nah, Rest Parameter sedikit berbeda.
Rest Pattern digunakan dalam destructuring.
Rest Parameter digunakan pada parameter function.
Contoh:
function addNumbers(...numbers) {
console.log(numbers);
}
Sekarang kita bisa memanggil:
addNumbers(1, 2);
numbers menjadi:
[1, 2]
Kalau:
addNumbers(1, 2, 5, 7);
maka:
numbers
menjadi:
[1, 2, 5, 7]
Kalau:
addNumbers(10, 20, 30, 40, 50, 60);
maka:
numbers
menjadi:
[10, 20, 30, 40, 50, 60]
11. Kenapa Rest Parameter berguna?
Biasanya function mempunyai jumlah parameter yang sudah ditentukan.
Contoh:
function addNumbers(num1: number, num2: number) {
return num1 + num2;
}
Function tersebut secara konsep menerima:
num1
num2
Jadi:
addNumbers(10, 20);
→ cocok.
Tapi kalau kita ingin:
addNumbers(1, 2, 3, 4, 5);
kita ingin function tersebut bisa menerima berapa pun jumlah angka.
Di sinilah Rest Parameter berguna.
12. Membuat Rest Parameter di TypeScript
Syntax-nya:
function addNumbers(...numbers: number[]) {
// ...
}
Artinya:
numbersadalah parameter yang dapat menerima jumlah argument berapa pun, dan semua argument tersebut akan dikumpulkan menjadi arraynumber[].
Misalnya:
addNumbers(1, 2);
di dalam function:
numbers = [1, 2]
Kalau:
addNumbers(1, 2, 5, 7);
maka:
numbers = [1, 2, 5, 7]
13. Perhatikan perbedaan “parameter” dan “argument”
Ini penting untuk memahami Rest Parameter.
Misalnya:
function addNumbers(...numbers: number[]) {
}
numbers adalah parameter.
Sedangkan ketika kita melakukan:
addNumbers(1, 2, 3, 4);
maka:
1
2
3
4
adalah arguments.
Rest Parameter bertugas mengumpulkan arguments tersebut menjadi array:
Arguments
1 2 3 4
│ │ │ │
└──┴──┴──┘
↓
numbers
↓
[1, 2, 3, 4]
14. Contoh sederhana
function printNumbers(...numbers: number[]) {
console.log(numbers);
}
printNumbers(10, 20, 30);
Output:
[10, 20, 30]
Kemudian:
printNumbers(1, 2, 3, 4, 5);
Output:
[1, 2, 3, 4, 5]
Jadi jumlah argument bisa fleksibel.
15. Mengapa lecture menggunakan for?
Karena setelah semua arguments dikumpulkan menjadi array, kita bisa memperlakukannya seperti array biasa.
Misalnya:
function addNumbers(...numbers: number[]) {
let count = 0;
for (let i = 0; i < numbers.length; i++) {
count += numbers[i];
}
return count;
}
Sekarang:
console.log(addNumbers(1, 2));
hasil:
3
Kemudian:
console.log(addNumbers(1, 2, 5, 7));
hasil:
15
Dan:
console.log(addNumbers(10, 20, 30, 40));
hasil:
100
16. Cara kerja Rest Parameter secara visual
Ketika kita memanggil:
addNumbers(1, 2, 5, 7);
JavaScript secara konsep melakukan:
1
2
5
7
│
│ Rest Parameter
↓
[1, 2, 5, 7]
Kemudian function menerima:
numbers = [1, 2, 5, 7]
Setelah itu kita bisa:
numbers.length
numbers[0]
numbers[1]
numbers.forEach(...)
numbers.map(...)
karena numbers adalah array.
17. Rest Parameter bukan berarti function menerima array
Ini kesalahan pemahaman yang sering terjadi.
Ketika kita punya:
function addNumbers(...numbers: number[]) {
}
kita memanggilnya seperti ini:
addNumbers(1, 2, 3, 4);
Bukan:
addNumbers([1, 2, 3, 4]);
Karena function tersebut menerima arguments satu per satu, lalu Rest Parameter mengumpulkannya menjadi array.
18. Kalau kita passing array bagaimana?
Kalau kita punya:
const numbers = [1, 2, 3, 4];
dan function:
function addNumbers(...numbers: number[]) {
console.log(numbers);
}
Kita bisa menggunakan Spread Operator:
addNumbers(...numbers);
Yang terjadi:
numbers
[1, 2, 3, 4]
...numbers
↓
1, 2, 3, 4
↓
function arguments
↓
Rest Parameter
↓
[1, 2, 3, 4]
Nah, di sini kita bisa melihat Spread dan Rest bekerja bersama.
19. Ini contoh yang sangat bagus untuk membedakan keduanya
const numbers = [1, 2, 3, 4];
function printNumbers(...values: number[]) {
console.log(values);
}
printNumbers(...numbers);
Ada dua ..., tetapi tugasnya berbeda.
Yang pertama:
...numbers
berada ketika kita memanggil function.
Ini adalah:
Spread
Dia membongkar:
[1, 2, 3, 4]
menjadi:
1, 2, 3, 4
Yang kedua:
...values
berada pada parameter function.
Ini adalah:
Rest Parameter
Dia mengumpulkan:
1, 2, 3, 4
menjadi:
[1, 2, 3, 4]
20. Spread dan Rest seperti membuka dan mengemas
Ini analogi yang sangat mudah diingat.
Bayangkan sebuah kardus:
📦 [1, 2, 3, 4]
Spread
Membuka kardus:
📦
↓
1 2 3 4
Rest
Mengumpulkan barang-barang:
1 2 3 4
\ | | /
↓
📦 [1,2,3,4]
Jadi:
SPREAD
📦 → 1 2 3 4
"bongkar"
REST
1 2 3 4 → 📦
"kemas"
21. Perbedaan Spread vs Rest Pattern
Sekarang kita bandingkan secara langsung.
Spread
const numbers = [1, 2, 3];
const newNumbers = [10, ...numbers];
Spread:
[1,2,3]
↓
1 2 3
Kemudian masuk ke array baru:
[10,1,2,3]
Rest Pattern
const numbers = [1, 2, 3];
const [first, ...rest] = numbers;
Rest:
[1,2,3]
↓
first = 1
sisanya:
2,3
↓
rest = [2,3]
Jadi arahnya berlawanan:
SPREAD
container → values
REST
values → container
22. Perbedaan Rest Pattern vs Rest Parameter
Ini juga penting.
Keduanya sama-sama “rest”, tetapi konteksnya berbeda.
Rest Pattern
Digunakan pada destructuring:
const [first, ...rest] = numbers;
atau:
const { name, ...details } = user;
Tujuannya:
Mengambil sisa data saat destructuring.
Rest Parameter
Digunakan pada parameter function:
function sum(...numbers: number[]) {
}
Tujuannya:
Mengumpulkan semua arguments function ke dalam array.
23. Visualisasi ketiganya
...
│
┌──────────┼──────────┐
│ │ │
SPREAD REST PATTERN REST PARAMETER
│ │ │
bongkar sisa data kumpulkan
│ │ │
↓ ↓ ↓
[1,2,3] [1,2,3] sum(1,2,3)
↓ ↓ ↓
1,2,3 1 → first [1,2,3]
2,3
↓
rest
24. Tentang aturan “kiri dan kanan assignment operator”
Lecture memberikan rule:
Rest di sebelah kiri assignment, spread di sebelah kanan.
Ini berguna sebagai shortcut untuk contoh tertentu, tetapi jangan dianggap sebagai aturan universal.
Misalnya:
const [a, ...rest] = numbers;
Memang:
...rest
↓
left side
dan:
const result = [...numbers];
Spread ada di:
right side
Tetapi Rest Parameter:
function sum(...numbers: number[]) {}
tidak memiliki assignment operator = di situ.
Jadi rule yang lebih aman dan benar untuk diingat adalah:
Lihat fungsinya, bukan hanya posisi kiri/kanan
=.
Spread
Membuka/membongkar iterable atau properties.
[...numbers]
{...user}
someFunction(...numbers)
Rest
Mengumpulkan nilai menjadi satu tempat.
const [a, ...rest] = numbers;
const { name, ...details } = user;
function sum(...numbers) {}
Ini mental model yang lebih kuat.
25. Contoh Rest Pattern Object + Spread Object
Keduanya bisa dipakai bersamaan.
Misalnya:
const user = {
name: "John",
age: 28,
city: "Jakarta"
};
Kita ambil name, lalu kumpulkan sisanya:
const { name, ...details } = user;
Sekarang:
name
// "John"
details
// {
// age: 28,
// city: "Jakarta"
// }
Kemudian kita bisa membuat object baru:
const employee = {
...details,
company: "Google"
};
Hasil:
{
age: 28,
city: "Jakarta",
company: "Google"
}
Di sini:
...details
pada destructuring → Rest
sedangkan:
...details
pada object baru → Spread
Simbolnya sama, tugasnya berbeda berdasarkan konteks.
26. Rest Parameter dengan parameter biasa
Rest Parameter juga bisa dikombinasikan dengan parameter biasa.
Contoh:
function greet(message: string, ...names: string[]) {
console.log(message);
console.log(names);
}
Kita bisa:
greet(
"Hello",
"John",
"Mark",
"Mary"
);
Hasilnya secara konsep:
message
↓
"Hello"
names
↓
["John", "Mark", "Mary"]
Ini sangat berguna ketika function memiliki:
beberapa parameter wajib + jumlah parameter tambahan yang fleksibel.
27. Rest Parameter harus menjadi parameter terakhir
Sama seperti Rest Pattern, Rest Parameter harus berada di akhir.
Benar:
function sum(a: number, b: number, ...numbers: number[]) {
}
Tidak benar:
function sum(...numbers: number[], a: number) {
}
Karena lagi-lagi JavaScript akan bingung:
Mana yang termasuk numbers?
Mana yang harus diberikan kepada a?
Jadi:
parameter biasa → parameter biasa → ...rest
28. Contoh function penjumlahan yang lebih sederhana
Lecture menggunakan for...in. Untuk memahami konsep Rest Parameter, kita sebenarnya bisa menggunakan for...of, karena yang ingin kita ambil adalah value.
function addNumbers(...numbers: number[]): number {
let total = 0;
for (const number of numbers) {
total += number;
}
return total;
}
Kemudian:
console.log(addNumbers(1, 2));
→
3
console.log(addNumbers(1, 2, 5, 7));
→
15
console.log(addNumbers(10, 20, 30, 40));
→
100
29. Bahkan bisa menggunakan reduce
Karena numbers adalah array:
function addNumbers(...numbers: number[]): number {
return numbers.reduce(
(total, number) => total + number,
0
);
}
Kemudian:
addNumbers(1, 2, 3, 4, 5);
→
15
Ini menunjukkan satu hal penting:
Setelah Rest Parameter mengumpulkan arguments, parameter tersebut dapat diperlakukan seperti array biasa.
30. Hubungan dengan materi Spread sebelumnya
Sekarang kita bisa melihat hubungan kedua lecture ini.
Misalnya:
const users = ["John", "Mark", "Mary"];
Spread
const allUsers = ["Ravi", ...users];
Spread membongkar:
users
["John","Mark","Mary"]
↓ spread
John, Mark, Mary
menjadi:
["Ravi", "John", "Mark", "Mary"]
Rest
const [first, ...others] = users;
Rest mengumpulkan:
John
Mark
Mary
↓
first = John
others = [Mark, Mary]
Jadi:
SPREAD
[John, Mark, Mary]
↓
John, Mark, Mary
REST
John, Mark, Mary
↓
[Mark, Mary]
31. Cara mengingat paling mudah
Saya sarankan jangan menghafal:
“Kalau di kiri berarti rest, kalau di kanan berarti spread.”
Lebih baik hafalkan arah datanya.
Spread
SATU CONTAINER
↓
BANYAK VALUE
[1,2,3]
↓
1,2,3
Rest
BANYAK VALUE
↓
SATU CONTAINER
1,2,3
↓
[1,2,3]
32. Cheat Sheet
| Konsep | Fungsi | Contoh |
|---|---|---|
| Spread Array | membongkar array | [...numbers] |
| Spread Object | membongkar properties | {...user} |
| Rest Pattern Array | mengumpulkan sisa element | [a, ...rest] |
| Rest Pattern Object | mengumpulkan sisa properties | {name, ...rest} |
| Rest Parameter | mengumpulkan arguments function | function sum(...numbers) |
33. Ringkasan dengan satu contoh
Perhatikan ini:
const numbers = [1, 2, 3, 4, 5];
Destructuring biasa
const [a, b] = numbers;
a = 1
b = 2
Rest Pattern
const [a, b, ...rest] = numbers;
a = 1
b = 2
rest = [3, 4, 5]
Spread
const copy = [...numbers];
copy = [1, 2, 3, 4, 5]
Array baru dibuat.
Rest Parameter
function printNumbers(...values: number[]) {
console.log(values);
}
printNumbers(1, 2, 3, 4, 5);
Di dalam function:
values = [1, 2, 3, 4, 5]
34. Mental model terakhir
Bayangkan kita punya:
📦 [1, 2, 3, 4, 5]
Spread:
📦
↓
1 2 3 4 5
Rest Pattern:
1 2 3 4 5
↓ ↓ └──────┘
a b rest
↓
[3,4,5]
Rest Parameter:
function sum(...numbers)
sum(1,2,3,4,5)
1 2 3 4 5
↓
numbers
↓
[1,2,3,4,5]
Jadi kalimat paling penting dari lecture ini adalah:
Spread membongkar isi, sedangkan Rest mengumpulkan isi.
Dan khusus Rest:
Rest Pattern mengumpulkan sisa data saat destructuring, sedangkan Rest Parameter mengumpulkan arguments yang dikirim ke function.
I can also create an image explaining the flow Spread vs Rest secara visual agar lebih mudah diingat.