通俗浅显的理解promise中的then
通俗浅显的理解promise中的then
- 先看一下下面4个Promise到底有什么区别呢?
- 执行第一个方法:
- 执行第二个方法:
- 执行第三个方法:
- 执行第四个方法:
文章原文出处:博主petruslaw
Promise,ES6中定义的规范,不会使用Promise,都不敢说自己用过ES6,大部分介绍Promise的规范的文章对于新手小白来说看得云里雾里,且并不是通俗易懂。本文通过实例介绍讲述Promise中then的的最通俗应用理解,代码建立在不出现异常的情况的操作下,不严谨之处,请以官方规范为标准。
先看一下下面4个Promise到底有什么区别呢?
func().then(function () {return cb();
});func().then(function () {cb();
});func().then(cb());func().then(cb);
如果你知道答案,以下内容你可以不用继续。
上面的代码过于简单,运行时话需要稍微进行一点扩展,每个方法中都打印出promise上一步的调用值,为了方便我给每个方法加了一个下标输出,分别是1、2、3、4。
let func = function() {return new Promise((resolve, reject) => {resolve('返回值');});/*resolve和reject是函数,接收函数的函数是高阶函数。此处的高阶函数就是Promise()内部代码整体(匿名箭头函数)。 箭头函数内部没有this,其this指向箭头函数的上一个临近函数/对象。*/
};let cb = function() {return '新的值';
}func().then(function () {return cb();
}).then(resp => {console.warn(resp);console.warn('1 =========<');
});func().then(function () {cb();
}).then(resp => {console.warn(resp);console.warn('2 =========<');
});func().then(cb()).then(resp => {console.warn(resp);console.warn('3 =========<');
});func().then(cb).then(resp => {console.warn(resp);console.warn('4 =========<');
});
不卖关子,直接看结果
首先要明白Promise中then方法会干什么事情!
官方文档是这样定义的:
一个 promise 必须提供一个 then 方法以访问其当前值、终值和据因。
promise 的 then 方法接受两个参数:
promise.then(onFulfilled, onRejected) Todo:这里只介绍onFulfilled,所以删除了关于onRejected的规范定义
onFulfilled 和 onRejected 都是可选参数。
如果 onFulfilled 不是函数,其必须被忽略
如果 onFulfilled 是函数:
当 promise 执行结束后其必须被调用,其第一个参数为 promise 的终值
在 promise 执行结束前其不可被调用
其调用次数不可超过一次
用通(ren)俗(hua)的话来说:
then方法提供一个供自定义的回调函数,若传入非函数,则会忽略当前then方法。
回调函数中会把上一个then中返回的值当做参数值供当前then方法调用。
then方法执行完毕后需要返回一个新的值给下一个then调用(没有返回值默认使用undefined)。
每个then只可能使用前一个then的返回值。
直观的图:
有了上面的定义我们带着三个疑问来回答问题:
- 上一个then中传入了回调函数吗?
- 上一个then中提供了返回值吗?
- 若上一个then中若提供了返回值,返回了什么?
执行第一个方法:
func().then(function () {return cb();
}).then(resp => {console.warn(resp);console.warn('1 =========<');
});
function () {return cb();
}
显而易见,是传入了回调函数的
回调函数中把cb执行后的返回值当做then中的返回值,所以输出了“新的值”;
执行第二个方法:
func().then(function () {cb();
}).then(resp => {console.warn(resp);console.warn('2 =========<');
});
function () {cb();
}
then回调方法,只是执行了cb方法,并没有return值,定义中讲过若then没有返回值,提供给下一个then使用的参数就是undefined,所以打印出来的是undefined;
执行第三个方法:
func().then(cb()).then(resp => {console.warn(resp);console.warn('3 =========<');
});
then中cb()执行后返回的并不是一个函数,在Promise规范中会自动忽略调当前then,所以会把func中的返回值供下一个then使用,输出了“返回值”
执行第四个方法:
func().then(cb).then(resp => {console.warn(resp);console.warn('4 =========<');
});
第一个方法在回调内部返回cb执行后的值,第四个方法则直接把cb当做回调,第一个方法与第四个方法异曲同工之妙,所以也输出了“新的值”。
题目出处:link
Promise规范:link
通俗浅显的理解promise中的then相关推荐
- 深入理解nodejs中的异步编程
文章目录 简介 同步异步和阻塞非阻塞 javascript中的回调 回调函数的错误处理 回调地狱 ES6中的Promise 什么是Promise Promise的特点 Promise的优点 Promi ...
- 大白话讲解Promise(二)理解Promise规范
上一篇我们讲解了ES6中Promise的用法,但是知道了用法还远远不够,作为一名专业的前端工程师,还必须通晓原理.所以,为了补全我们关于Promise的知识树,有必要理解Promise/A+规范,理解 ...
- [转]深入理解CSS中的层叠上下文和层叠顺序
http://www.zhangxinxu.com/wordpress/2016/01/understand-css-stacking-context-order-z-index/ 零.世间的道理都是 ...
- 如何简单地理解Python中的if __name__ == '__main__'
如何简单地理解Python中的if __name__ == '__main__' 文章目录: 一.摘要 二. 程序入口 虽然已经知道这个具体的用法,但是这篇文章有很多细节写的还是很好,决定转载一下,日 ...
- php event loop,理解javascript中的事件循环(Event Loop)
背景 在研究js的异步的实现方式的时候,发现了JavaScript 中的 macrotask 和 microtask 的概念.在查阅了一番资料之后,对其中的执行机制有所了解,下面整理出来,希望可以帮助 ...
- es5如何实现promise_彻底理解Promise对象——用es5语法实现一个自己的Promise(上篇)...
众所周知javascript语言的一大特色就是异步,这既是它的优点,同时在某些情况下也带来了一些的问题.最大的问题之一,就是异步操作过多的时候,代码内会充斥着众多回调函数,乃至形成回调金字塔.为了解决 ...
- ES6——举个例子理解Promise的原理和使用
1. Promise 之前 1.1 回调函数 回调函数:把函数A当作参数传递给另一个函数B调用,那么A就是回调函数. 一些例子 具名回调 function 你有几只狗(fn){fn('一只狗') } ...
- java 值栈的结构_Struts2 | 深入浅出理解struts2中的值栈
在没有struts框架的时候,我们通常在Servlet中使用域对象进行存值和取值,将其作为载体来承载页面和后台之间的数据传递. 在struts2中,我们又有了一种新的机制来进行数据的传递. 那就是st ...
- SVM支持向量机通俗导论(理解SVM的三层境界)
神文 转自july:http://blog.csdn.net/v_july_v/article/details/7624837 支持向量机通俗导论(理解SVM的三层境界) 作者:July .致谢:pl ...
最新文章
- Java String 到底是引用传递还是值传递?
- Linux 基础知识(十)DNS服务器主从复制,子域授权
- stc单片机入门c语言,谈谈单片机入门
- php content-type: multipart/mixed,{error:invalid multipart format} 这是什么原因,我已经在HEADER中设置了Content-...
- 面向对象--内置方法
- leetcode题解191-位1的个数
- diff算法_Virtual Dom和Diff算法
- Netbeans 安装和配置 C/C++ 支持
- ASP.NET AJAX入门系列(7):使用客户端脚本对UpdateProgress编程
- Redis实现分布式爬虫
- Bailian4074 积水量【序列处理】
- 仿抖音上下滑动播放视频
- 5G组网方案和频谱规划
- 杰理AD14N/AD15N---长按键开关机怎么实现
- 算法 图8 How Long Does It Take
- SEO新手入门系列2022(五):挖掘关键词
- 华为pppoe简单配置实验
- 『与善仁』Appium基础 — 3、移动端测试环境搭建(三)之AVD模拟器安装
- Bert入门:使用Bert运行MRPC的demo成功案例
- Java集合--阻塞队列(LinkedBlockingQueue)