Javascript异步流程控制之串行执行详解


Posted in Javascript onSeptember 27, 2020

这篇文章主要讲一下如何串行执行一组异步任务,例如有下面几个任务,在这里我们用setTimeout模拟一个异步任务:

let taskA = () => setTimeout(() => console.log('run task A'), 100);
let taskB = () => setTimeout(() => console.log('run task B'), 50);
let taskC = () => setTimeout(() => console.log('run task C'), 150);

直接运行

taskA(); taskB(); taskC();

是达不到顺序执行A,B,C 的三个任务的效果的。

首先我们看一下最传统的做法,通过回调的方式在一个任务执行完成之后调用下一个任务:

let taskA = setTimeout(() => {
 console.log('run task A');
 taskB();
}, 100);
let taskB = setTimeout(() => {
 console.log('run task B');
 taskC();
}, 50);
let taskC = setTimeout(() => {
 console.log('run task B');
}, 150);

第二种方法是将每一个任务封装成一个返回Promise的函数, 然后使用使用Promise的链式调用达到串行执行的目的:

let taskA = () => new Promise((resolve, reject) => {
 setTimeout(() => {
  console.log('run task A');
  resolve();
 }, 100);
})
let taskB = () => new Promise((resolve, reject) => {
 setTimeout(() => {
  console.log('run task B');
  resolve();
 }, 50);
})
let taskC = () => new Promise((resolve, reject) => {
 setTimeout(() => {
  console.log('run task C');
  resolve();
 }, 150);
})
function runTasks2() {
  console.log('tasks 2');
  taskA().then(taskB).then(taskC);
}

假设任务的数量不确定,可以通过下面的方式来执行:

function runTasks3(tasks) {
  console.log('tasks 3');
  let pro = tasks[0]();
  for (let i = 1; i < tasks.length; i++) {
  pro.then(tasks[i]);
  }
}

借助于es7的async和await,我们还可以对上面的函数一种写法:

async function runTasks3_1(tasks) {
  for (let i = 0; i < tasks.length; i++) {
  await tasks[i]();
  }
}

在文章的最后我们自己来实现一个串行执行器, 用于执行一组串行任务:

function async(tasks) {
  const count = tasks.length;
  let index = 0;
  const next = () => {
   if (index >= count) return;
   const task = tasks[index++];
   task(next);
  }
  next(0);
}

函数的使用方式如下:

async([
   next => setTimeout(() => { console.log('taskA ...'); next() }, 100),
   next => setTimeout(() => { console.log('taskB ...'); next() }, 50),
   next => setTimeout(() => { console.log('taskC ...'); next() }, 30)
 ]);

在每一个子任务中我们通过调用next函数继续执行下一个子任务。

在具体的使用中可能会遇到函数之间传递参数的情况,即前一个任务的执行结果需要作为下一个任务的入参,这些都可以对上面的例子稍作修改就可以了~~

到此这篇关于Javascript异步流程控制之串行执行详解的文章就介绍到这了,更多相关Javascript串行执行内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Javascript 相关文章推荐
基于jQuery架构javascript基础体系
Jan 01 Javascript
JavaScript实现倒计时代码段Item1(非常实用)
Nov 03 Javascript
jQuery的实例及必知重要的jQuery选择器详解
May 20 Javascript
js数组常用操作方法小结(增加,删除,合并,分割等)
Aug 02 Javascript
原生JS取代一些JQuery方法的简单实现
Sep 20 Javascript
简单易懂的天气插件(代码分享)
Feb 04 Javascript
解决vue单页使用keep-alive页面返回不刷新的问题
Mar 13 Javascript
微信小程序仿知乎实现评论留言功能
Nov 28 Javascript
详解Vue.js自定义tipOnce指令用法实例
Dec 19 Javascript
VUE 自定义组件模板的方法详解
Aug 30 Javascript
JS实现长图上下滚动效果
Mar 19 Javascript
vue.js watch经常失效的场景与解决方案
Jan 07 Vue.js
vue+elementUI 实现内容区域高度自适应的示例
Sep 26 #Javascript
Openlayers实现测量功能
Sep 25 #Javascript
openlayers4.6.5实现距离量测和面积量测
Sep 25 #Javascript
JQuery Ajax如何实现注册检测用户名
Sep 25 #jQuery
Openlayers测量距离与面积的实现方法
Sep 25 #Javascript
基于JS实现操作成功之后自动跳转页面
Sep 25 #Javascript
OpenLayers3实现测量功能
Sep 25 #Javascript
You might like
使用PHP维护文件系统
2006/10/09 PHP
php 表单提交大量数据发生丢失的解决方法
2014/03/03 PHP
PHP用反撇号执行外部命令
2015/04/14 PHP
php+curl 发送图片处理代码分享
2015/07/09 PHP
PHP结合jQuery实现找回密码
2015/07/22 PHP
关于PHP文件的自动运行方法分析
2016/05/13 PHP
php处理多图上传压缩代码功能
2018/06/13 PHP
php图片裁剪函数
2018/10/31 PHP
php实现文件上传基本验证
2020/03/04 PHP
关于javascript function对象那些迷惑分析
2011/10/24 Javascript
Jquery 选中表格一列并对表格排序实现原理
2012/12/15 Javascript
setInterval()和setTimeout()的用法和区别示例介绍
2013/11/17 Javascript
JS实现动态修改table及合并单元格的方法示例
2017/02/20 Javascript
Webpack打包慢问题的完美解决方法
2017/03/16 Javascript
微信小程序scroll-view实现字幕滚动
2018/07/14 Javascript
mpvue+vuex搭建小程序详细教程(完整步骤)
2018/09/30 Javascript
基于js实现逐步显示文字输出代码实例
2020/04/02 Javascript
[56:35]DOTA2上海特级锦标赛主赛事日 - 5 总决赛Liquid VS Secret第一局
2016/03/06 DOTA
Python实现删除Android工程中的冗余字符串
2015/01/19 Python
Python中super关键字用法实例分析
2015/05/28 Python
Django实现组合搜索的方法示例
2018/01/23 Python
使用requests库制作Python爬虫
2018/03/25 Python
好的Python培训机构应该具备哪些条件
2018/05/23 Python
Python使用tkinter库实现文本显示用户输入功能示例
2018/05/30 Python
关于matplotlib-legend 位置属性 loc 使用说明
2020/05/16 Python
python 用opencv实现图像修复和图像金字塔
2020/11/27 Python
html5使用window.postMessage进行跨域实现数据交互的一次实战
2021/02/24 HTML / CSS
西班牙自行车和跑步商店:Alltricks
2018/07/07 全球购物
外贸实习生自荐信范文
2013/11/24 职场文书
复核员上岗演讲稿
2014/01/05 职场文书
护理专业自荐书
2014/06/04 职场文书
内科护士节演讲稿
2014/09/11 职场文书
python自动化之如何利用allure生成测试报告
2021/05/02 Python
使用golang编写一个并发工作队列
2021/05/08 Golang
如何解决springcloud feign 首次调用100%失败的问题
2021/06/23 Java/Android
pytorch中的 .view()函数的用法介绍
2022/03/17 Python