preface
Async is simply a syntactic sugar for Generator, and you can look at Generator functions in the previous article before reading this article. Understanding Generator makes it easy to understand why Async is the perfect solution for asynchronous programming.
directory
- Async function
- Principle of Async function
- Common about
async
The pen test
Async function
const fs = require('fs');
const readFile = function (fileName) {
return new Promise(function (resolve, reject) {
fs.readFile(fileName, function(error, data) {
if (error){
return reject(error);
}
resolve(data);
});
});
};
const foo = function* () {
const f1 = yield readFile('/src/lib');
const f2 = yield readFile('/src/utils');
console.log(f1.toString());
console.log(f2.toString());
};
Copy the code
Write Generator foo as async, like this:
const asyncReadFile = async function () {
const f1 = await readFile('/src/lib');
const f2 = await readFile('/src/utils');
console.log(f1.toString());
console.log(f2.toString());
};
Copy the code
As you can see, the async function simply replaces the asterisk (*) of the Generator function with async, replaces yield with await, and nothing more.
The Async function is a generator-based improvement, as shown in the following four points
- Built-in actuators.
Generator
A function must be executed by an executor. That’s where it comes inThunk
Functions andco
Module, andasync
Functions come with their own actuators.async
Functions are executed just like normal functions.
asyncReadFile();
Copy the code
-
Better semantics. Async and await are semantic clearer than asterisks and yield. Async means that there is an asynchronous operation in a function, and await means that the following expression needs to wait for the result.
-
Wider adaptability. Even though Generator functions can be executed automatically with the help of the CO module, the CO module can only be followed by Thunk functions or Promise objects, while async functions can be followed by await commands with Promise objects and primitive values (numeric, string, and Boolean values, etc.). But this is automatically switched to immediate Resolved Promise)
-
The return value is Promise. Aysnc returns a Promise, which is much more convenient than Generator returns an Iterator.
Async functions can be thought of as multiple asynchronous operations wrapped as a Promise object, and await commands are syntactic sugar for internal THEN commands.
In short, the Generator function is a coroutine that JS learns from other languages and implements according to the single-thread characteristics of JS, but it is much more troublesome to use. Each time, it has to write its own executor, while async function is born to solve these repetitive tasks. The async function encapsulates the Generaor function and the autoexecutor perfectly.
The implementation principle of async function
This is to wrap the Generator function and the auto-executor in one function.
async function fn(args) {
// ...
}
function fn(args) {
return spawn(function* () {
// ...})}Copy the code
All async functions can be written in the second form above, where the spawn function is the auto-executor.
// Accept a Generator as an argument and return a Promise object
function spawn(genF) {
return new Promise(function(resolve, reject) {
// Execute genF to get an internal pointer object
const gen = genF();
function step(nextF) {
let next;
// Perform error handling
try {
next = nextF();
} catch(e) {
return reject(e);
}
if(next.done) {
return resolve(next.value);
}
// Convert next. Value to a Promise object
Promise.resolve(next.value).then(function(v) {
step(function() { return gen.next(v); });
}, function(e) {
step(function() { return gen.throw(e); });
});
}
// call step repeatedly
step(function() { return gen.next(undefined); });
});
}
Copy the code
As you can see, this is a combination of a Generator function and a Promise that implements an automatic executor that returns a Promise object
Common aboutasync
The pen test
- To implement a
sleep
: - Implement a traffic light: red 2 seconds, yellow 1 seconds, green 3 seconds
- use
async
implementationPromise.all()
The effect of
Implement a sleep
Output 1, 2, 3, 4, 5 at 1 second intervals
function sleep(interval) {
return new Promise(resolve= >{ setTimeout(resolve, interval); })}/ / usage
async function one2FiveInAsync() {
for (let i = 1; i <= 5; i++) {
console.log(i);
await sleep(1000);
}
}
one2FiveInAsync();
Copy the code
Implement a traffic light
Red 2 seconds, yellow 1 second, green 3 seconds
function sleep(duration) {
return new Promise(resolve= >{ setTimeout(resolve, duration); })}async function changeColor(color, duration) {
console.log('Current color', color);
await sleep(duration);
}
async function main() {
await changeColor('red'.2000);
await changeColor('yellow'.1000);
await changeColor('green'.3000);
}
main();
Copy the code
Use async to implement promise.all ()
Assume that getFoo and getBar are two functions that make ajax requests.
/ / write one
let [foo, bar] = await Promise.all([getFoo(), getBar()]);
/ / write two
let fooPromise = getFoo();
let barPromise = getBar();
let foo = await fooPromise;
let bar = await barPromise;
Copy the code
Both methods, getFoo and getBar, fire at the same time, thus shortening the execution time of the program.
This is just a simple example. Think about it and write the full code.
conclusion
async
The principle of the function isGenerator
Functions and autoactuators are wrapped up.Generator
That is, you can temporarily execute and pick up where you left off. For example, an interface request is sent, after which JS can do something else, and when the interface request comes back (the data comes in through Next), execution continues. But it doesn’t work automatically, so you need an autoexecutor,thunk
Functions andco
Modules are both, but Async gives us a better encapsulation.
about
This article started on my Github blog
Recently, WE launched a 100-day front-end advanced plan, which is mainly to dig into the principle behind each knowledge point. Welcome to follow the wechat public account “Mucode star”, and we will study together and punch the clock for 100 days.