Node.js 如何利用异步提升任务处理速度


Posted in Javascript onJanuary 07, 2019

今天在做一个小任务,需要调用阿里云的图像识别接口,对 62662 张照片进行场景识别,并将结果写到本地的 csv 文件中。

因为任务很简单,没想很多就开始码。自从有了 async/await 之后,已经很久不写 callback 了,所以上手就写成这样:

本文所有代码均有简化,只保留关键过程

async fetchSceneTags(imagePath) {
  try {
   const result = await callAliyunAPI(imagePath);
   return result.errno === 0 ? result.tags : [];
 } catch(error) {
   return [];    
 }
}

async function writeScene(paths) {
  for (let i = 0, len = paths.length; i < len; i++) {
    await tags = fetchSceneTags(paths[i])
    writeToFile(tags);
    writeStdout(`${i} / ${len}`);
  }
}

function start() {
  const paths = loadPaths();
  writeScene(paths);
}

运行起来以后没问题就放着忙别的去了。过了差不多 2 小时回来一看,才跑了 17180 张图,每分钟 144 张。这才意识到同步速度太慢了,于是停掉进程,将代码改成下面这样:

fetchSceneTagsAsync(imagePath, callback) {
  callAliyunAPI(imagePath)
    .then(result => {
   const tags = result.errno === 0 ? result.tags : [];
     callback(tags);
   })
    .catch(error => callback([]));
}

function writeSceneAsync(paths) {
  const callback = tags => {
    await tags = fetchSceneTagsAsync(paths[i])
    writeToFile(tags);
  }
  
  paths.forEach(path => fetchSceneTagsAsync(path, callback));
}

function start() {
  const paths = loadPaths();
  writeSceneAsync(paths);
}

跑了一下,直接停摆了。嗯,不能一下把请求全发出去,加一个 Throttle:

fetchSceneTagsAsync(imagePath, callback) {
  callAliyunAPI(imagePath)
    .then(result => {
   const tags = result.errno === 0 ? result.tags : [];
     callback(tags);
   })
    .catch(error => callback([]));
}

function throttle(paths, callback) {
  if(paths.length === 0) return;
  
  const sub = paths.splice(0, 10);
  sub.forEach(path => fetchSceneTagsAsync(path, callback));
 setTimeout(() => throttle(paths, callback), 1000)
}

function writeSceneAsync(paths) {
  const callback = tags => {
    await tags = fetchSceneTagsAsync(paths[i])
    writeToFile(tags);
  }
  
  throttle(paths, callback)
}

function start() {
  const paths = loadPaths();
  writeSceneAsync(paths);
}

重新启动服务,观察了一下,大约每分钟处理 568 张图片,速度提升约 4 倍。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
JQuery给元素绑定click事件多次执行的解决方法
May 29 Javascript
jquery获取radio值(单选组radio)
Oct 16 Javascript
jQuery中[attribute]选择器用法实例
Dec 31 Javascript
jQuery中unwrap()方法用法实例
Jan 16 Javascript
详解addEventListener的三个参数之useCapture
Mar 16 Javascript
javascript入门教程基础篇
Nov 16 Javascript
JavaScript中Form表单技术汇总(推荐)
Jun 26 Javascript
微信小程序实现自定义picker选择器弹窗内容
May 26 Javascript
React 实现拖拽功能的示例代码
Jan 06 Javascript
详解React服务端渲染从入门到精通
Mar 28 Javascript
javascript sort()对数组中的元素进行排序详解
Oct 13 Javascript
JS eval代码快速解密实例解析
Apr 23 Javascript
vue封装一个简单的div框选时间的组件的方法
Jan 06 #Javascript
如何封装了一个vue移动端下拉加载下一页数据的组件
Jan 06 #Javascript
浅谈在Vue.js中如何实现时间转换指令
Jan 06 #Javascript
浅谈Vue.js中如何实现自定义下拉菜单指令
Jan 06 #Javascript
react-router4按需加载(踩坑填坑)
Jan 06 #Javascript
React 实现拖拽功能的示例代码
Jan 06 #Javascript
Next.js实现react服务器端渲染的方法示例
Jan 06 #Javascript
You might like
PHP接收json 并将接收数据插入数据库的实现代码
2015/12/01 PHP
PHP访问数据库集群的方法小结
2016/03/14 PHP
JavaScript 事件参考手册
2008/12/24 Javascript
jQuery(1.3.2) 7行代码搞定跟随屏幕滚动的层
2009/05/21 Javascript
jquery checkbox全选、取消全选实现代码
2010/03/05 Javascript
给jqGrid数据行添加修改和删除操作链接(之一)
2011/11/04 Javascript
结合JQ1.9通过js正则判断各种浏览器版本的方法
2013/12/30 Javascript
js 动态为textbox添加下拉框数据源的方法
2014/04/24 Javascript
jquery实现拖拽调整Div大小
2015/01/30 Javascript
js代码验证手机号码和电话号码是否合法
2015/07/30 Javascript
js获取及判断键盘按键的方法
2015/12/01 Javascript
详解angular中如何监控dom渲染完毕
2017/01/03 Javascript
bootstrap 表单验证使用方法
2017/01/11 Javascript
作为老司机使用 React 总结的 11 个经验教训
2017/04/08 Javascript
浅析JavaScript中的特殊数据类型
2017/12/15 Javascript
详解layui弹窗父子窗口之间传参数的方法
2018/01/16 Javascript
Vue页面跳转动画效果的实现方法
2018/09/23 Javascript
ES6 fetch函数与后台交互实现
2018/11/14 Javascript
node.js实现上传文件功能
2019/07/15 Javascript
Vue+Koa2+mongoose写一个像素绘板的实现方法
2019/09/10 Javascript
关于vue里页面的缓存详解
2019/11/04 Javascript
微信小程序之导航滑块视图容器功能的实现代码(简单两步)
2020/06/19 Javascript
Python使用中文正则表达式匹配指定中文字符串的方法示例
2017/01/20 Python
python使用正则表达式来获取文件名的前缀方法
2018/10/21 Python
很酷的python表白工具 你喜欢我吗
2019/04/11 Python
pycharm编写spark程序,导入pyspark包的3中实现方法
2019/08/02 Python
基于Python获取城市近7天天气预报
2019/11/26 Python
解决TensorFlow模型恢复报错的问题
2020/02/06 Python
CSS3中Animation动画属性用法详解
2016/07/04 HTML / CSS
出国英文推荐信
2014/05/10 职场文书
珍惜时间演讲稿
2014/05/14 职场文书
领导干部群众路线个人对照检查材料思想汇报
2014/09/30 职场文书
五年级作文之想象作文
2019/10/30 职场文书
numpy数据类型dtype转换实现
2021/04/24 Python
「海贼王」112.9万粉丝纪念图标公布
2022/03/21 日漫
Win11怎么添加用户?Win11添加用户账户的方法
2022/07/15 数码科技