generator
async和await是generator的语法糖,想要搞清楚async和await必须知道generator;那么我们先来看看generator函数;
function * getAge() {
yield 1;
yield 2;
}
let gen = getAge();
console.log(gen.next());//{ value: 1, done: false }
console.log(gen.next());//{ value: 2, done: false }
console.log(gen.next());//{ value: undefined, done: true }
generator和普通函数的区别:
1.generator声明函数之前要加*
2.函数中有yield,可以控制函数的运行
generator传参问题
function * getAge() {
let a = yield 1;
console.log(a);//444
yield 2;
}
let gen = getAge();
console.log(gen.next());
console.log(gen.next(444));
generator传参可以将参数传在next函数中,给a赋值,但是第一个next()函数永远是undefined;如下
function * getAge(xxx) {
let a = yield 1;
console.log(a);//undefined
yield 2;
}
let gen = getAge();
console.log(gen.next(444));
console.log(gen.next());
generator函数运行过程
generator实现读取异步函数
现在有一个name和age的txt文件,我们通过name.txt读取age.txt里的内容;我这里的name中写的是age.txt,age.txt中写的是18;
let {promisify} = require('util');
let fs = require('fs');
let read = promisify(fs.readFile);
function * getAge() {
let name = yield read(`${__dirname}name.txt`, 'utf-8');
let age = yield read(`${__dirname}${name}`, 'utf-8');
}
let it = getAge();
let {value} = it.next();//返回的是读取name.txt的promise函数
value.then(data => {
let {value} = it.next(data)//将读取name文件的内容作为参数赋值给getAge函数中的name,同时这里的value是读取age.txt的promise函数
value.then(data => {
console.log(data)//18
})
});
async和await
上面层层嵌套看着很乱尤其是嵌套多的情况下,那么我们使用async和await实现一下这里只是将generator函数中的*换成了async,将yield换成了await
async function getAge1() {
let name = await read(`${__dirname}name.txt`, 'utf-8');
let age = await read(`${__dirname}${name}`, 'utf-8');
console.log(age);
}
getAge1()
我们将上面函数进行babel转义成es2015,就是将generaotr+promise结合起来实现了async和await函数
1 将async函数转换成generator
2.第一次执行next传参为undefined,上面我们也提到了第一次next的值是undefined
3.将上一次的返回值传递给下面的next函数,递归实现找打最后即可
let {promisify} = require('util');
let fs = require('fs');
let read = promisify(fs.readFile);
function asyncGeneratorStep(gen, resolve, reject, _next, key, arg) {
try {
var info = gen[key](arg);
var value = info.value;
} catch (error) {
reject(error);
return;
}
if (info.done) {
resolve(value);
} else {
//为了防止value是个普通值(不是promise),使用Promise.resolve包一层
Promise.resolve(value).then(_next);
}
}
function _asyncToGenerator(fn) {
return function () {
return new Promise(function (resolve, reject) {
var gen = fn();
function _next(value) {
asyncGeneratorStep(gen, resolve, reject, _next, "next", value);
}
_next(undefined);
});
};
}
function getAge1() {
return _getAge();
}
function _getAge() {
_getAge = _asyncToGenerator(function* () {
let name = yield read(`${__dirname}name.txt`, 'utf-8');
let age = yield read(`${__dirname}${name}`, 'utf-8');
});
return _getAge();
}
getAge1(); //让函数执行
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。