ES6에 도입된 제너레이터(generator)는 코드 블록의 실행을 일시 중지했다가 필요한 시점에 재개할 수 있는 특수한 함수이다. (모던 JS 딥다이브 참고)
(1) 제너레이터 함수는 함수 호출자에게 함수 실행의 제어권을 양도할 수 있다.
yield
(2) 제너레이터 함수는 함수 호출자와 함수의 상태를 주고받을 수 있다.
next
, yield
(3) 제너레이터 함수를 호출하면 제너레이터 객체를 반환한다.
function*
키워드를 사용하고, 하나 이상의 yield
표현식을 포함한다.yield
키워드는 제너레이터 함수의 실행을 일시 중지시키거나 yield
키워드 뒤에 오는 표현식의 평가 결과를 제너레이터 함수 호출자에게 반환한다.function* genFunc() {
yield 1;
}
const genFunc() = *() => {
yield 1;
}; // SyntaxError
제너레이터 함수를 호출하면 생성되는 제너레이터 객체는 이터러블이면서 이터레이터이다.
다시 말해, 제너레이터 객체는 반복할 수 있고, next()
메서드로 value
, done
속성의 값을 반환할 수 있다.
next 메서드를 호출하면 제너레이터 함수의 yield 표현식까지 코드 블록을 실행하고, value
와 done
프로퍼티 값으로 갖는 이터레이터 리절트 객체를 반환한다.
value
: yield된 값done
: 제너레이터 함수가 끝까지 실행되었는지 나타내는 불리언 값function* genFunc() {
yield 1;
yield 2;
}
const generator = genFunc();
console.log(generator.next()); // {value: 1, done: false}
function* genFunc() {
yield 1;
yield 2;
yield 3;
}
const generator = genFunc();
console.log(generator.next()); // {value: 1, done: false}
console.log(generator.next()); // {value: 2, done: false}
console.log(generator.next()); // {value: 3, done: false}
console.log(generator.next()); // {value: undefined, done: true}
위의 코드를 살펴보면,
yield
표현식으로 넘어갈 수 있는 next
메서드를 갖는다.next
메서드는 이터레이터 리절트 객체({value, done})을 반환한다.value
프로퍼티에는 yield
표현식에서 yield된 값이 할당된다.done
프로퍼티에는 제너레이터 함수가 끝까지 실행되었는지를 나타내는 불리언 값이 할당된다.next
메서드를 호출하면 value
에는 제너레이터 함수의 반환값(return 값)이 할당되고, done
에는 끝까지 실행되었다는 의미의 true
가 할당된다.generator.next() -> yield -> generator.next() -> yield -> ... -> generator.next() -> return
const fibonacci = (function* () {
let [pre, cur] = [0, 1];
while(true) {
[pre, cur] = [cur, pre + cur];
yield cur;
}
}());
for (const num of fibonacci) {
if (num > 10000) break;
console.log(num); // 1 2 3 ... 6765
}
next
메서드와 yield
표현식을 통해 함수 호출자와 함수의 상태를 주고받을 수 있다.출처
📖 모던 자바스크립트 Deep Dive
🔗https://developer.mozilla.org/ko/docs/Web/JavaScript/Guide/Iterators_and_generators#generator_%EC%8B%AC%ED%99%94