Wechat official account: [Dafront-end Yizhan] Follow Dafront-end Yizhan. Questions or suggestions, welcome the public account message.

This is the 11th day of my participation in the August Wenwen Challenge.More challenges in August

define

Generator functions are an extremely flexible addition to ECMAScript 6, with the ability to pause and resume code execution within a function block. Generators allow you to customize iterators and implement coroutines.

A function name preceded by an asterisk (*) indicates that it is a generator

function* generatorFnA() {}
function * generatorFnB() {}
function *generatorFnC() {}
Copy the code

Asterisks that identify generator functions are not affected by white space on either side, and all three are reasonable definitions.

The generator object starts out in a suspended state. Like iterators, generator objects implement the Iterator interface and therefore have the next() method. Calling this method causes the generator to start or resume execution

function* generatorFn() {} 
const g = generatorFn(); 
console.log(g); // generatorFn {<suspended>} 
console.log(g.next); // f next() { [native code] }
Copy the code

The generator function will only start execution after the first call to the next() method

function* generatorFn() { console.log('foo'); } let generatorObject = generatorFn(); generatorObject.next(); // fooCopy the code

Generator objects implement the Iterable interface and their default iterators are self-referential

function* generatorFn() {}
const g = generatorFn(); 
console.log(g === g[Symbol.iterator]()) // true
Copy the code

Yield expression

The yield keyword allows the generator to stop and start execution, and is where the generator is most useful. The generator function executes normally until the yield keyword is encountered. When this keyword is encountered, execution stops and the state of the function scope is preserved. A stopped generator function can only resume execution by calling the next() method on the generator object

function* generatorFn() { 
 yield 'foo'; 
 yield 'bar'; 
 return 'baz'; 
} 
let generatorObject = generatorFn(); 
console.log(generatorObject.next()); // { done: false, value: 'foo' } 
console.log(generatorObject.next()); // { done: false, value: 'bar' } 
console.log(generatorObject.next()); // { done: true, value: 'baz' }
Copy the code

A generator function that exits with the yield keyword is in the done: false state; Generator functions that exit with the return keyword are in the done: true state.

The yield keyword can only be used inside a generator function and will throw an error if used elsewhere.

You can use an asterisk to enhance the behavior of yield, allowing it to iterate over an iterable, thus producing one value at a time

function* generatorFn() { yield* [1, 2, 3]; } let g = generatorFn(); for (const x of g) { console.log(x); } // 1/2/3Copy the code

Premature termination generator

Both the return() and throw() methods can be used to force the generator into a closed state

function* generatorFn() {} 
const g = generatorFn(); 
console.log(g); // generatorFn {<suspended>} 
console.log(g.next); // f next() { [native code] } 
console.log(g.return); // f return() { [native code] } 
console.log(g.throw); // f throw() { [native code] }
Copy the code
  • Terminates the generator in return mode
function* generatorFn() { 
 for (const x of [1, 2, 3]) { 
 yield x; 
 } 
} 
const g = generatorFn(); 
console.log(g); // generatorFn {<suspended>} 
console.log(g.return(4)); // { done: true, value: 4 } 
console.log(g); // generatorFn {<closed>}
Copy the code

Once a generator object is in the closed state using the return () method, it cannot be recovered. As shown above, the generator is in the closed state and the next () method is called to show the done:true state

  • Throw terminates the generator
function* generatorFn() { 
 for (const x of [1, 2, 3]) { 
 yield x; 
 } 
} 
const g = generatorFn(); 
console.log(g); // generatorFn {<suspended>} 
try { 
 g.throw('foo'); 
} catch (e) { 
 console.log(e); // foo 
} 
console.log(g); // generatorFn {<closed>}
Copy the code

The throw() method injects a supplied error into the generator object when paused. If the error is not handled, the generator is shut down. However, if the error is handled internally by the generator function, the generator is not shut down and execution can resume. Error handling skips the corresponding yield, so in this case a value is skipped

function* generatorFn() { 
 for (const x of [1, 2, 3]) { 
 try { 
 yield x; 
 } catch(e) {} 
 } 
}
const g = generatorFn(); 
console.log(g.next()); // { done: false, value: 1} 
g.throw('foo'); 
console.log(g.next()); // { done: false, value: 3}
Copy the code

If the generator object has not yet started executing, the error thrown by the call to throw() will not be caught inside the function, because it is equivalent to throwing an error outside the function block.














Pay attention to the bottom [Big front End station]
Let’s learn and make progress together

[Share, like, watch] Let more people join us