博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Nodejs Promise对象
阅读量:2054 次
发布时间:2019-04-28

本文共 5759 字,大约阅读时间需要 19 分钟。

Promise对象

1. promise用来做什么?

我们的需求是一次的去执行异步代码

我们的做法是在异步请求成功后的回调函数里,执行下一个异步请求

但是这样就出现了回调地狱(回调函数中嵌套了回调函数,代码的阅读性 低,维护不变,让人看着害怕)

promise就是用来解决回调地狱的

回调地狱示例:

// 需求:一次的读取a,b,c这三个文件const fs = require("fs");// 读a文件fs.readFile(`${
__dirname}/etc/a.txt`, "utf-8", (err, data) => {
if (err) {
console.log(err); } else {
console.log(data); // 读b文件 fs.readFile(`${
__dirname}/etc/b.txt`, "utf-8", (err, data) => {
if (err) {
console.log(err); } else {
console.log(data); // 读c文件 fs.readFile(`${
__dirname}/etc/c.txt`, "utf-8", (err, data) => {
if (err) {
console.log(err); } else {
console.log(data); } }); } }); }});

2. promise工作流程

es6的语法,es6.ruanyifeng.com

Promise对象是一个构造函数 ,用来生成promise实例

Promise构造函数接受一个函数作为参数

这个作为参数的函数,又有两个参数,这两个参数分别是resolve和reject

这两个参数它们也是函数,只不过这两个函数由 javascript 引擎提供,不用自己部署

异步操作成功后调用resolve()方法,他内部调用了then()里面的第一个参数函数

异步操作成功后调用reject()方法,他内部调用了then()里面的第二个参数函数.

const fs = require("fs");// 调用Promise构造函数,创建一个promise的实例let p = new Promise((resolve, reject) => {
// 写异步操作(读文件) fs.readFile(`${
__dirname}/etc/a.txt`, "utf-8", (err, data) => {
if (!err) {
// 操作成功(读文件成功) resolve(data); // 调用resolve方法 // 调用then()里面的第一个参数函数 } else {
reject(err); // 调用reject方法 // 调用then()里面的第二个参数函数 } });});p.then( (data) => {
console.log(data); }, (err) => {
console.log(err); });

3. promise原理

Promise对象代表一个异步操作.

有三种状态: pending (进行中)、fulfilled (已成功)和rejected (已失败)

Promise对象的状态改变,只有两种可能:从pending变 为fulfilled和从pending变为rejected。

只有异步操作的结果,可以决定当前是哪一种状态,任何其他操作都无法改变这个状态

如果异步操作成功了(读文件成功了),从pending (进行中)变为 fulfilled (已成功) ;

如果异步操作失败了(读文件失败了),从pending (进行中)变为 rejected (已失败) ;

状态如果已经确定了, 就不会再去改变这个状态了

4. promise特点及其封装

Promise新建后就会立即执行

所以不要在promise里面写其他的代码,只写这个异步操作的代码就可以了

const fs = require("fs");function getPromise(filename) {
// 调用Promise构造函数,创建一个promise的实例 return new Promise((resolve, reject) => {
// 写异步操作(读文件) fs.readFile(`${
__dirname}/etc/${
filename}.txt`, "utf-8", (err, data) => {
if (!err) {
// 操作成功(读文件成功) resolve(data); // 调用resolve方法 // 调用then()里面的第一个参数函数 } else {
reject(err); // 调用reject方法 // 调用then()里面的第二个参数函数 } }); });}// console.log(getPromise("a"));getPromise("a").then( (data) => {
console.log(data); }, (err) => {
console.log(err); });

5. promise正确写法

promise如何解决回调地狱

-》 链式编程解决

**我们用promise解决的问题:让异步操作有顺序,并且不能有回调地狱 **

让异步操作有顺序本质是:

异步操作实际上是没有顺序的

在异步操作成功后的回调函数里返回另外的promise,调用他的then方法

const fs = require("fs");function getPromise(filename) {
// 调用Promise构造函数,创建一个promise的实例 return new Promise((resolve, reject) => {
// 写异步操作(读文件) fs.readFile(`${
__dirname}/etc/${
filename}.txt`, "utf-8", (err, data) => {
if (!err) {
// 操作成功(读文件成功) resolve(data); // 调用resolve方法 // 调用then()里面的第一个参数函数 } else {
reject(err); // 调用reject方法 // 调用then()里面的第二个参数函数 } }); });}// console.log(getPromise("a"));getPromise("a") .then((data) => {
console.log(data); //调用函数得到一个读b文件的promise对象并返回 return getPromise("b"); }) .then((data) => {
console.log(data); //调用函数得到一个读c文件的promise对象并返回 return getPromise("c"); }) .then((data) => {
console.log(data); });

6. promise的其他方法

  • catch()

    能够抓取错误的

    const fs = require("fs");function getPromise(filename) {
    // 调用Promise构造函数,创建一个promise的实例 return new Promise((resolve, reject) => {
    // 写异步操作(读文件) fs.readFile(`${
    __dirname}/etc/${
    filename}.txt`, "utf-8", (err, data) => {
    if (!err) {
    // 操作成功(读文件成功) resolve(data); // 调用resolve方法 // 调用then()里面的第一个参数函数 } else {
    reject(err); // 调用reject方法 // 调用then()里面的第二个参数函数 } }); });}// console.log(getPromise("a"));getPromise("a") .then((data) => {
    console.log(data); //调用函数得到一个读b文件的promise对象并返回 return getPromise("b"); }) .then((data) => {
    console.log(data); //调用函数得到一个读c文件的promise对象并返回 return getPromise("c"); }) .then((data) => {
    console.log(data); }) .catch((err) => {
    console.log(err); });
  • all()

    const fs = require("fs");function getPromise(filename) {
    // 调用Promise构造函数,创建一个promise的实例 return new Promise((resolve, reject) => {
    // 写异步操作(读文件) fs.readFile(`${
    __dirname}/etc/${
    filename}.txt`, "utf-8", (err, data) => {
    if (!err) {
    // 操作成功(读文件成功) resolve(data); // 调用resolve方法 // 调用then()里面的第一个参数函数 } else {
    reject(err); // 调用reject方法 // 调用then()里面的第二个参数函数 } }); });}let p1 = getPromise("a");let p2 = getPromise("b");let p3 = getPromise("c");// Promise.all()方法用于将多个 Promise 实例,包装成一个新的 Promise 实例let pAll = Promise.all([p1, p2, p3]);// 一个都不能少,每一个promise都要读取成功才会成功,相当于是并且pAll.then((data) => {
    console.log(data);});
  • race

    const fs = require("fs");function getPromise(filename) {
    // 调用Promise构造函数,创建一个promise的实例 return new Promise((resolve, reject) => {
    // 写异步操作(读文件) fs.readFile(`${
    __dirname}/etc/${
    filename}.txt`, "utf-8", (err, data) => {
    if (!err) {
    // 操作成功(读文件成功) resolve(data); // 调用resolve方法 // 调用then()里面的第一个参数函数 } else {
    reject(err); // 调用reject方法 // 调用then()里面的第二个参数函数 } }); });}let p1 = getPromise("a");let p2 = getPromise("b");let p3 = getPromise("c");// Promise.race()方法同样是将多个 Promise 实例,包装成一个新的 Promise 实例let pRace = Promise.race([p1, p2, p3]);// 只要有一个promise执行成功,那这个pRace就成功,相当于是或者pRace.then((data) => {
    console.log(data);});

转载地址:http://mcclf.baihongyu.com/

你可能感兴趣的文章
【雅思】【写作】【大作文】Discuss both views and give your own opinion
查看>>
【托业】【金山词霸】21-42
查看>>
【托业】【金山词霸】单词1-20
查看>>
【Python】脚本运行报错:IndentationError: unindent does not match any outer indentation level...
查看>>
【JMeter】前置处理器
查看>>
【Linux】top命令详解
查看>>
【黑盒测试】测试用例的常用方法
查看>>
【Linux】阿里云服务器部署--禅道
查看>>
【Loadrunner】Loadrunner 手动关联技术
查看>>
【性能测试】性能测试表
查看>>
【Mock】mock基础、简单的单元测试代码练习。
查看>>
【Loadrunner】Loadrnner 参数化策略
查看>>
【WebDriver】WebDriver 常用操作
查看>>
【Selenium】selenium中隐藏元素如何定位?
查看>>
【Mock】【接口测试】【面试】mock-server 环境搭建—加分项!
查看>>
【English】【托业】【四六级】写译高频词汇
查看>>
【托业】【新东方全真模拟】01~02-----P5~6
查看>>
【托业】【新东方全真模拟】03~04-----P5~6
查看>>
【托业】【新东方托业全真模拟】TEST05~06-----P5~6
查看>>
【托业】toeic托业必背核心词汇_修正版
查看>>