// 定义一个队列构造器 function queue(files) { // 使用Promise.resolve(val)生成一个Promise实例promise // promise的状态已转换为Resolved状态, // 这时promise仍可通过then方法获取到Resolved的结果val(这里的val为空,所以是undefined) let promise = Promise.resolve(); // 遍历一次传入的数组 files.forEach(file => { // promise对象添加then方法,并将then方法的返回值重新赋值给promise并传入resolve回调, // 因为只传了一个函数(这个函数没有参数,所以没法捕获上一次操作完成返回的值, // 事实上,楼主也没有在每次完成返回值,因为resolve()中没有给值。)参数, // 所以reject的回调为undefined promise = promise.then(() => { // then.resolve回调中返回了一个新的Promise实例,新的实例通过构造的方式生成, // 构造传入了"resolve"这样一个名字的函数参数,作为promise的resolve回调,没有reject return new Promise(resolve => { // 新构造的Promise实例的resolve回调中执行异步上传方法 doThing(file, () => { //访问接口 // 完成后resolve这个promise resolve(); }); }); }); }); // 返回了新的promise引用,事实上,这个promise引用就已经是个队列了 return promise; } // 这一步调用之后,做了什么事情?从这里再看这个queue内部的执行过程, // 调用之后,第一个上传文件的操作就会立即启动,上传完成之后就会继续上传下一个, // 直到这数组中都传完, 最后一个操作的resolve被下面这个then捕获 //获取了最后一个promise实例成功后resolve的值. queue([file1, file2, file3]).then(data => { // 打印resolve的值 console.log(data); }); 递归的方法:(实测运行成功) function doThing(file) { return new Promise((resolve) => { setTimeout(() => { console.log('doThing', file) resolve('result:' + file) }, 500) }) } function queue(files, data = []) { return new Promise((resolve) => { if (files.length > 0) { let file = files.shift(); doThing(file).then((res) => { data.push(res) resolve(queue(files, data)) }) } else { resolve(data) } }) } queue(['file1', 'file2', 'file3']).then(data => { console.log(data); });

Promise 队列
文章版权及转载声明
作者:问几许本文地址:https://wenjixu.com/blog/45.html发布于 5年前 ( 2018-09-30 )
文章转载或复制请以超链接形式并注明出处问几许
还没有评论,来说两句吧...