网站首页 > 博客文章 正文
ES6 规定, Promise对象是一个构造函数, 下面代码生成了一个Promise实例。
const promise = new Promise(function(resolve, reject){
resolve(100) //调用成功的回调函数
// reject(500) //调用失败的回调函数
})
//console.log(promise);
promise
.then(() => console.log("成功,表示得到我们想要的结果,可以继续往下执行"))
.then(() => console.log("成功可以无限调用then方法"))
.catch(() => console.log("失败了,也表示得到结果,但是结果并非我们所愿"))
Promise构造函数接受一个函数作为参数, 该函数的两个参数分别是resolve和reject。它们是两个函数, 由 JavaScript 引擎提供, 不用自己部署。
resolve 表示成功执行的回调函数
reject 表示失败执行的回调函数
pending 表示等待中, 或者进行中, 还没有得到结果
Promise使用场景
下面用实际案例进行演示, 封装一个读文件duwenjian()函数, 这个函数接收url作为路径参数:
在浏览器环境中, 用Ajax按顺序读取三个文件, 为了解决回调黑洞问题, 使用Promise对象:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<title>Document</title>
</head>
<body>
<button>请求数据</button>
</body>
<script type="text/javascript" src="data/jquery-3.3.1.min.js"></script>
<script type="text/javascript">
// const promise = new Promise(function(resolve, reject){
// resolve()
// //reject()
// })
// console.log(promise)
function duwenjian(url){
return new Promise(function(resolve, reject){
$.ajax({
url: url,
success: function(data){
resolve(data)
// console.log(data)
},
error: function(err){
reject(err)
// console.log(err)
}
})
})
}
$('button').click(function(){
duwenjian("data/1.json").then((data)=>{
console.log('1成功了', data)
return duwenjian("data/2.json")
}).then((data)=>{
console.log('2成功了', data)
return duwenjian("data/3.json")
}).then((data)=>{
console.log('3成功了',data)
})
});
</script>
</html>
在Nodejs环境中读文件
var fs = require('fs');
function duwenjian(url){
return new Promise(function(resolve, reject){
fs.readFile(url, "utf8", (err, data)=>{
if(err){
reject(err); //失败执行
return;
}
resolve(data); //成功执行
})
})
}
duwenjian("./data/1.txt").then((data)=>{
console.log(data)
return duwenjian("./data/2.txt")
})
.then((data)=>{
console.log(data)
return duwenjian("./data/3.txt")
})
.then((data)=>{
console.log(data)
})
.catch((err)=>{
console.log()
})
回调黑洞问题解决了, 将原来的"嵌套模式"变为"队列模式"。
Promise实例生成以后, 可以用then方法分别指定resolved状态和rejected状态的回调函数。
then方法可以接受两个回调函数作为参数。
第一个回调函数是Promise对象的状态变为resolved时调用。
第二个回调函数是Promise对象的状态变为rejected时调用。
其中, 第二个函数是可选的, 不一定要提供, 可以使用catch()方法替代。这两个函数都接受Promise对象传出的值作为参数。
promise.then((data)=>{
console.log(data);
},(err)=>{
console.log(err)
})
等价于以下写法:
promise.then((data)=>{
console.log(data);
})
.catch((err)=>{
console.log(err)
})
Promise的实例拥有then()和catch()方法用来处理成功和失败的事情, 这两方法是定义在原型对象中的。
异步语句的成功, 要将数据通过resolve(数据)传出去, 这个数据将成为then函数的参数。
异步语句的失败, 要将错误信息通过reject(err)传出去, 这个数据将成catch函数的参数。
Promise一定是某个函数的唯一返回值才有意义, 本例中, Promise就是duwenjian函数的返回值!!
Promise表示"承诺", 当异步完毕之后, 一定会执行resolve。
Promise.all()方法
Promise.all()方法接收一个Promise对象组成的数组作为参数, 当这个数组所有的Promise对象状态都变成resolved或者rejected的时候, 它才会去调用then方法。
function Async1(){
return new Promise(function(resolve, reject){
setTimeout(function(){
console.log('异步任务1执行完成');
resolve('数据1');
}, 2000);
});
}
function Async2(){
return new Promise(function(resolve, reject){
setTimeout(function(){
console.log('异步任务2执行完成');
resolve('数据2');
}, 2000);
});
}
function Async3(){
return new Promise(function(resolve, reject){
setTimeout(function(){
console.log('异步任务3执行完成');
resolve('数据3');
//reject('出错了')
}, 2000);
});
}
//使用all方法执行多个异步函数
Promise.all([Async1(), Async2(), Async3()])
.then((result)=>{
console.log(result); //成功的结果
})
.catch((err)=>{
console.log(err); //失败的结果
})
异步任务1执行完成
异步任务3执行完成
异步任务2执行完成
(3) ["数据1", "数据2", "数据3"]
Promise.race()
all方法的效果是「谁跑的慢, 以谁为准执行回调」
race方法的效果是「谁跑的快, 以谁为准执行回调」
这就是race方法, 这个词本来就是赛跑的意思。
race的用法与all一样, 我们把上面Async1延时改为1秒来看一下:
Promise.race([Async1(), Async2(), Async3()])
.then((result)=>{
console.log(result); //成功的结果
})
.catch((err)=>{
console.log(err); //失败的结果
})
这三个异步操作同样是并行执行的。结果你应该可以猜到, 1秒后Async1已经执行完了, 此时then里面的就执行了。
异步任务1执行完成
数据1
异步任务2执行完成
异步任务3执行完成
在then的回调开始执行时, Async2()和Async3()并没有停止, 仍旧在执行。于是再过1秒后, 输出了他们结束的标志。
这个race有什么用呢?使用场景还是很多的,比如可以用race给某个异步请求设置超时时间,并且在超时后执行相应的操作,代码如下:
//请求某个图片资源的函数
function requestImg(){
return new Promise(function(resolve, reject){
var img = new Image();
img.src = 'xxxxxx';
img.onload = function(){
resolve(img);
}
});
}
//延时函数,用于给请求计时
function timeout(){
return new Promise(function(resolve, reject){
setTimeout(function(){
reject('图片请求超时!');
}, 5000);
});
}
Promise.race([requestImg(), timeout()])
.then(function(result){
console.log(result);
})
.catch(function(err){
console.log(err);
});
总结:
Promise构造函数, 自己身上有all、race、reject、resolve等方法, 原型上有then、catch等方法。
猜你喜欢
- 2024-10-27 前端面试大全:手写 Promise(前端手机端面试题)
- 2024-10-27 Javascript ES6中 Generator的?async/await Promise 了解一下?
- 2024-10-27 Promise 中 race 方法的目的是什么
- 2024-10-27 ES6 Promise 的最佳实践(es6 promise作用)
- 2024-10-27 ES6学习(17):彻底搞懂 async 和 await,轻松掌握异步编程!
- 2024-10-27 自己造轮子,超详细、简单的Promise对象原理讲解及代码实现
- 2024-10-27 JavaScript ES6 语法特性介绍(javascript的基本语法遵循的标准是____。)
- 2024-10-27 图解 Promise 实现原理(一):基础实现
- 2024-10-27 可视化的 js:动态图演示 Promises & Async/Await 的过程
- 2024-10-27 前端ES6中Promise原理之进阶篇(二)
你 发表评论:
欢迎- 06-23MySQL合集-mysql5.7及mysql8的一些特性
- 06-23MySQL CREATE TABLE 简单设计模板交流
- 06-23MYSQL表设计规范(mysql设计表注意事项)
- 06-23MySQL数据库入门(四)数据类型简介
- 06-23数据丢失?别慌!MySQL备份恢复攻略
- 06-23MySQL设计规范(mysql 设计)
- 06-23MySQL数据实时增量同步到Elasticsearch
- 06-23MySQL 避坑指南之隐式数据类型转换
- 最近发表
- 标签列表
-
- powershellfor (55)
- messagesource (56)
- aspose.pdf破解版 (56)
- promise.race (63)
- 2019cad序列号和密钥激活码 (62)
- window.performance (66)
- qt删除文件夹 (72)
- mysqlcaching_sha2_password (64)
- ubuntu升级gcc (58)
- nacos启动失败 (64)
- ssh-add (70)
- jwt漏洞 (58)
- macos14下载 (58)
- yarnnode (62)
- abstractqueuedsynchronizer (64)
- source~/.bashrc没有那个文件或目录 (65)
- springboot整合activiti工作流 (70)
- jmeter插件下载 (61)
- 抓包分析 (60)
- idea创建mavenweb项目 (65)
- vue回到顶部 (57)
- qcombobox样式表 (68)
- vue数组concat (56)
- tomcatundertow (58)
- pastemac (61)
本文暂时没有评论,来添加一个吧(●'◡'●)