Generators in JavaScript. Code examples open

Generators in JavaScript. Code examples

Approved. Code works!
This is exactly the working code that is verified by the moderator or site administrators

Generators are a special type of function that are used to generate values. Generators are defined using the asterisk * symbol after the function keyword.

For example:

    function* getNumber() {
        yield 5;//generate number 5
    }

    const numberGenerator = getNumber();
    const next = numberGenerator.next();
    console.log(next);  // {value: 5, done: false}

The generator function returns an iterator.

yield – an operator that returns a value from a generator.

To get the value from the generator, the next() method is used.

    const next = numberGenerator.next();

And if we look at the console output, we can see that this method returns the following data:

    { value: 5, done: false }

That is, in fact, an object is returned, the value property of which contains the actual generated value. And the done property indicates whether we have reached the end of the generator.

Now let’s change the code:

    function* getNumber() {
        yield 5;
    }

    const numberGenerator = getNumber();
    let next = numberGenerator.next();
    console.log(next);//{value: 5, done: false}
    next = numberGenerator.next();
    console.log(next);//{value: undefined, done: true}

The getNumber generator function generates only one value, the number 5. Therefore, when called again, the value property will be undefined, and the done property will be true, that is, the work of the generator is completed.

A generator can create/generate many values:

    function* getNumber() {
        yield 5;
        yield 25;
        yield 125;
    }

    const numberGenerator = getNumber();
    console.log(numberGenerator.next());//{value: 5, done: false}
    console.log(numberGenerator.next());//{value: 25, done: false}
    console.log(numberGenerator.next());//{value: 125, done: false}
    console.log(numberGenerator.next());//{value: undefined, done: true}

We can return elements from an array in the generator:

    const numbers = [5, 25, 125, 625];

    function* getNumber() {
        for (const n of numbers) {
            yield n;
        }
    }

    const numberGenerator = getNumber();
    console.log(numberGenerator.next().value);  // 5
    console.log(numberGenerator.next().value);  // 25

Some indefinite time may elapse between two successive calls to next(), and there may be some other actions between them.

A generator does not necessarily contain only the definition of yield statements. It can also contain more complex logic.

Using generators, it is convenient to create infinite sequences:

    function* points() {

        let x = 0;
        let y = 0;
        while (true) {
            yield { x: x, y: y };
            x += 2;
            y += 1;
        }
    }
    let pointGenerator = points();

    console.log(pointGenerator.next().value);
    console.log(pointGenerator.next().value);
    console.log(pointGenerator.next().value);

In console:

    { x: 0, y: 0 }
    { x: 2, y: 1 }
    { x: 4, y: 2 }

Stopping Generator

We can terminate the generator using the return() method:

    function* getNumber() {
        yield 5;
        yield 25;
        yield 125;
    }
    const numberGenerator = getNumber();
    console.log(numberGenerator.next());    // {value: 5, done: false}
    numberGenerator.return();   //shutting down the generator
    console.log(numberGenerator.next());    // {value: undefined, done: true}

Getting generator values in a loop

Since we use an iterator to get values, we can use a for…of loop:

    function* getNumber() {
        yield 5;
        yield 25;
        yield 125;
    }

    const numberGenerator = getNumber();

    for (const num of numberGenerator) {
        console.log(num);//5, 25, 125
    }

While loop

    function* getNumber() {
        yield 5;
        yield 25;
        yield 125;
    }

    const numberGenerator = getNumber();

    while (!(item = numberGenerator.next()).done) {
        console.log(item.value);
    }

Passing Data to the Generator

Through the parameters, we can pass some data to the generator. For example:

    function* getNumber(start, end, step) {
        for (let n = start; n <= end; n += step) {
            yield n;
        }
    }

    const numberGenerator = getNumber(0, 8, 2);

    for (num of numberGenerator) {
        console.log(num);
    }

Another example is to define a generator that will return data from an array:

Passing data to the next method

Using next(), you can pass data to the generator. The data passed to this method can be obtained in the generator function through the previous call to the yield statement:

    function* getNumber() {
        const n = yield 5;      // get the value numberGenerator.next(2).value
        console.log("n:", n);
        const m = yield 5 * n;  // get the value numberGenerator.next(3).value
        console.log("m:", m);
        yield 5 * m;
    }
    const numberGenerator = getNumber();

    console.log(numberGenerator.next().value);      // 5
    console.log(numberGenerator.next(2).value);     // 10
    console.log(numberGenerator.next(3).value);     // 15

On the second call to the next() method:

    numberGenerator.next(2).value

We can retrieve the data passed through it by assigning the result of the first call to the yield statement:

    const n = yield 5;

That is, here the constant n will be equal to 2, since the number 2 is passed to the next() method.

We can then use this value, for example, to generate a new value:

    const m = yield 5 * n;

Error Handling

With the throw() function, we can throw an exception in the generator. As a parameter, an arbitrary value is passed to this function, which represents information about the error:

    function* generateData() {
        
		try {
            yield "Tom";
            yield "Bob";
            yield "Hello Work";
        }
		
        catch (error) {
            console.log("Error:", error);
        }
    }

    const personGenerator = generateData();
    console.log(personGenerator.next());        // {value: "Tom", done: false}
    personGenerator.throw("Something wrong");   // Error: Something wrong
    console.log(personGenerator.next());        // {value: undefined, done: true}

After calling the throw() function, the generator exits, and then when we call the next() method, we get the result {value: undefined, done: true}.

0

More

Leave a Reply

Your email address will not be published. Required fields are marked *

How many?: 22 + 22

lil-code© | 2022 - 2024
Go Top
Authorization
*
*
Registration
*
*
*
*
Password generation