The development of origin

  • Promise is a little bit redundant to write and always return New Promise and then zipper
  • The Generator manually controls where to wait and where to execute (typically waiting for asynchronous operations)
  • Async /await is an automatic Generator

Yield and NEET parameters

If var a = yield exp, then exp will be returned before the assignment is performed, and exp will change depending on the next argument

The next method of the traverser object runs as follows:

(1) When a yield statement is encountered, the following operation is paused and the value of the expression immediately following the yield is used as the value of the returned object’s value property.

(2) The next time the next method is called, the execution continues until the next yield statement is encountered.

(3) If no new yield statement is encountered, run until the end of the function until the return statement, and use the value of the expression following the return statement as the value of the returned object’s value property.

(4) If the function does not have a return statement, the value attribute of the returned object is undefined.

The next method can take an argument that is treated as the return value of the previous yield statement.

function * f() { for( let i =0; true; i++){ let reset = yield i; if(reset){ i = -1; } } } let g = f(); console.log(g.next()); console.log(g.next()); console.log(g.next(true)); // The yield return value is set to true, causing reset to be set to trueCopy the code

Output result:

{ value: 0, done: false }
{ value: 1, done: false }
{ value: 0, done: false }
Copy the code

As you can see in the last step, we substituted the value of I with true passed in from Next, resulting in I = -1 + 1 = 0.

Let’s look at another example:

function * f2(x){
    var y = 2 * ( yield ( x + 1));
    var z = yield (y / 3);
    return (x + y + z);
}

var r1= f2(5);
console.log(r1.next());
console.log(r1.next());
console.log(r1.next());

var r2= f2(5);
console.log(r2.next());
console.log(r2.next(12));
console.log(r2.next(13));
Copy the code

Output result:

{ value: 6, done: false }
{ value: NaN, done: false }
{ value: NaN, done: true }

{ value: 6, done: false }
{ value: 8, done: false }
{ value: 42, done: true }
Copy the code

Note that the yield clause itself does not return a value, or that it always returns undefined. When next comes around, the next argument simply reassigns the value of the expression following yield, thus ignoring yield. That is, if next does not pass, yield itself returns no value, so we get NaN. But if next passes in a specific value, that value replaces the yield and becomes the true return value.

async/await

To put it simply, async functions are equivalent to self-executing Generator functions, equivalent to having a state machine waiting for the return of the await part and automatically performing the next step after the return. The advantage of async over Promise is that it takes the result returned each time asynchronously from then to the outermost method, so it doesn’t need to be called in a chain, but can be written synchronously. More intuitive and better suited for handling concurrent calls. But async must start with a Promise object, so async is usually used in conjunction with a Promise.

Async function usage

Async is just a syntactic sugar for a Generator function, so why the name? Naturally, there is a reason. Async is’ asynchronous’ and ‘await’ is short for async wait. So it makes sense that async is used to declare that a function is asynchronous and await is used to wait for an asynchronous method to complete

Let’s look at an example to understand the async command

Async function test() {return "Async does what?" ; } const result = test(); console.log(result)Copy the code

Output: What does Promise {‘async do? As you can see, the output is a Promise object **! 六四运动

So async returns a Promise object. If async returns a Promise directly, it wraps the Promise object with promise.resolve ()

Note that in general, an await is considered to be waiting for an async function to complete. Rather, it is awaiting a representation that evaluates to either a Promise object or some other value.

That is, await can be followed not only by promises, but also by ordinary functions or direct quantities.

At the same time, async can be understood as an operator used to form expressions whose results depend on what it waits for

  • Wait until the non-Promise object expression results in what it waits for
  • Waiting for the Promise object await blocks the following code, waiting for the Promise object resolve to retrieve the value of resolve as the result of the expression
Function fun1(value) {retrun new Promise((resolve,reject)=> {setTimeout(function(callback){resolve(value++)}, 2000); })} fun1(0). Then (value)=> {return new Promise((resolve,reject)=> {setTimeout(function(callback){resolve(value++)}, 2000); }). Then ((value)=> {return new Promise((resolve,reject)=> {setTimeout(function(callback){resolve(value++)}, 2000); }). Then (value)=>{console.log(value)} function fun1(value) {retrun new Promise((resolve,reject)=> { SetTimeout (function(callback){resolve(value++)}, 2000); })} // return promise instance async function asy() {let v = 0 v = await fun1(v) // wait for promise's resolve value as the result on the right of = v = await fun1(v) v = await fun1(v) v =  await fun1(v) console.log(v) } asy() //4Copy the code