写点什么

【Promise 源码学习】第十六篇 - 了解 co 库

作者:Brave
  • 2021 年 12 月 10 日
  • 本文字数:1262 字

    阅读完需:约 4 分钟

一,前言


上篇,主要介绍了 generator 生成器函数的使用和实现原理,主要涉及以下几个点:


  • generator 简介:特性、用法、功能分析;

  • generator 实现原理分析;


前面的 Promise 仅仅是对异步回到进行了优化,在 Promise 的内部依然还是存在回调的,所以实际上并没有解决“回调地狱”的问题;


最终解决方案还要使用 async/await,async/await 是基于 generator 的语法糖,而为了搞清楚 async/await 的原理,需要先对 generator、co 进行了解;


本篇,继续介绍 co 库:自动执行 Generator 生成器函数;


二,co 库的简介

1,co 库的作用

  • 用于自动执行 Generator 生成器函数;备注:co 库的作者是 TJ Holowaychuk,而他同时也是 express\koa 的作者;

2,co 库的使用

  • 安装 co 库 : npm install co

  • 测试场景:读取 a.txt 得到结果 b.txt;读取 b.txt 得到结果 c;


const util = require('util');const fs = require('fs');let readFile = util.promisify(fs.readFile)
// generator 生成器函数function * read() { let data = yield readFile('./a.txt','utf8'); data = yield readFile(data,'utf8'); return data;}
// 方法一:Generatorlet it = read(); // 生成器函数返回一个 Iterator 迭代器对象let {value:v1, done:d1} = it.next(); // 注意:第一个next传参是无效的v1.then(data=>{ console.log(data) // b.txt let {value:v2, done:d2} = it.next(data); // 将第一次的结果作为第二次的入参 return v2}).then(data=>{ console.log(data) // 执行结果:c})
// 方法二:使用 co 库const co = require('co')// co 方法:包装 generator 生成器函数,内部自动执行完成,返回一个 promiseco(read()).then(data=>{ console.log(data); // 执行结果:c})
复制代码


对比 Generator 和 co 两种方案:

  • 后者的实现,明显更加清晰和简洁:无需分步执行、获取中间结果、判断是否结束;

  • co 使 generator 能够自动执行完成,并返回 primise 形式的结果;



三,co 库的实现


手写一个 co 方法:主要使用了”异步迭代“的思想;


/** * 自动执行迭代器 * @param {*} it generator执行返回的迭代器函数 * @returns  */function co(it) {  return new Promise((resolve, reject) => {    function next(data) { // 将上一次的结果作为下一次的入参      let { value, done } = it.next(data);      if (done) { // 迭代器执行完成,返回最终结果        resolve(value);      } else {        // 备注:使用 Promise.resolve 将 value 包装成Promise        // 成功:说明迭代器还没有执行完,继续递归调用 next,直至迭代器完成        Promise.resolve(value).then(next, reject);// 注意此处的 next 传入的是当前 function      }    }
next();// 第一次调用 next 时,传参是无效的 })}
复制代码



四,结尾


本篇,主要介绍了 co 库的使用和实现原理,主要涉及以下几个点:


  • co 库的简介:特性、用法、功能分析;

  • co 库的实现和原理分析;


下一篇,继续介绍 async/await:generator 语法糖,嵌套回调问题的最终解决方案;

用户头像

Brave

关注

还未添加个人签名 2018.12.13 加入

还未添加个人简介

评论

发布
暂无评论
【Promise 源码学习】第十六篇 - 了解 co 库