Skip to main content

Що таке ітератор?

Що таке ітератор

Ітератор - це об'єкт, який покроково перебирає (ітерує) елементи іншої структури даних - масиву, рядка, Set, Map тощо.

Він реалізує спеціальний інтерфейс - у нього є метод next(), який повертає об'єкт вигляду:

javascript
{ value: <значення>, done: <логічний прапорець> }

Приклад простого ітератора

javascript
const iterator = { current: 1, last: 3, next() { if (this.current <= this.last) { return { value: this.current++, done: false }; } else { return { done: true }; } } }; console.log(iterator.next()); // { value: 1, done: false } console.log(iterator.next()); // { value: 2, done: false } console.log(iterator.next()); // { value: 3, done: false } console.log(iterator.next()); // { done: true }

Ітератор сам зберігає свій стан і знає, де він "зупинився".


Що робить ітератор особливим

Ітератори - це універсальний спосіб перебору. Наприклад, масиви, рядки, Map і Set вже вбудовано ітеровані - у них є спеціальний символьний ключ Symbol.iterator.


Приклад вбудованого ітератора масиву

javascript
const arr = [10, 20, 30]; const iterator = arr[Symbol.iterator](); console.log(iterator.next()); // { value: 10, done: false } console.log(iterator.next()); // { value: 20, done: false } console.log(iterator.next()); // { value: 30, done: false } console.log(iterator.next()); // { value: undefined, done: true }

Тобто for...of під капотом робить те саме.


for...of та ітератори

javascript
const arr = [1, 2, 3]; for (const value of arr) { console.log(value); } // 1 // 2 // 3

Цикл for...of автоматично викликає arr[Symbol.iterator]() і перебирає значення, поки done: true.


Створення власного ітерованого об'єкта

Щоб зробити свій об'єкт "перебірним" (ітерованим), у ньому потрібно визначити метод з ключем Symbol.iterator.

javascript
const range = { from: 1, to: 5, [Symbol.iterator]() { let current = this.from; const last = this.to; return { next() { if (current <= last) { return { value: current++, done: false }; } else { return { done: true }; } } }; } }; for (const num of range) { console.log(num); // 1 2 3 4 5 }

Тепер range можна використовувати в for...of, Array.from(), ...spread та інших конструкціях.


Використання ітераторів в інших контекстах

КонструкціяЩо робить
for...ofПеребирає ітеровані значення
...spreadРозкриває ітератор
Array.from(iterable)Перетворює ітератор на масив
Деструктуризація [a, b] = iterableВитягує значення через ітератор

Приклад:

javascript
const set = new Set(['a', 'b', 'c']); const arr = [...set]; // ['a', 'b', 'c']

Працює, тому що у Set є вбудований Symbol.iterator.


Асинхронні ітератори

З'явилися в ES2018: асинхронні ітератори повертають проміси в next().

javascript
const asyncIterable = { async *[Symbol.asyncIterator]() { yield 'A'; yield 'B'; yield 'C'; } }; for await (const value of asyncIterable) { console.log(value); } // A // B // C

Це використовується для асинхронних потоків даних (наприклад, читання файлів, API-потоки).


Ітератор vs Ітерований об'єкт

ПоняттяЩо цеПриклад
Ітерований об'єкт (Iterable)Об'єкт, у якого є метод [Symbol.iterator]()масив, рядок, Set
Ітератор (Iterator)Об'єкт, у якого є метод next()результат виклику arr[Symbol.iterator]()

Приклад:

javascript
const arr = [1, 2, 3]; const iterator = arr[Symbol.iterator](); // ітератор

Короткий підсумок

ТермінОпис
ІтераторОб'єкт з методом next(), який повертає { value, done }
Ітерований об'єктОб'єкт, який реалізує метод [Symbol.iterator]()
doneПрапорець кінця послідовності (true - ітерацію завершено)
valueПоточне значення
Використовується вfor...of, spread, Array.from(), деструктуризація

Коротка відповідь

Для співбесіди
Premium

Коротка відповідь допоможе вам впевнено відповідати на цю тему під час співбесіди.