Promise/A+ 规范:诞生与原理初探

在 Philip Roberts 眼中,JavaScript 是一门单线程、异步、非阻塞、解释型脚本语言。我们在享受 JavaScript 异步编程带来的便捷的同时,也在为如何处理异步(或处理异步带来的冗杂的代码)而苦恼。但是,作为一门富有活力的编程语言,JavaScript 也在不断地完善自己的标准与规范,为众多 JavaScript 开发者解决这些苦恼。当我们在谈论如何处理异步时,我们可能会立刻想起回调函数(Callback Functions)。我们可以通过这种神奇的机制完成对每一个异步操作结果的处理。然而,随着我们的代码越来越复杂,异步操作也越来越多,而原始的回调方式暴露出的问题也越来越明显。 好在,Promise 的到来为我们解决了一部分问题。那么究竟是什么使 Promise 具有如此魅力,使得它一度被称为“下一代”异步编程方案呢?我们将在本文中从源码和底层原理层面探讨这些问题。在阅读这篇文章前,我们需要掌握以下内容: JavaScript 事件循环机制 异步编程的基本概念 JavaScript 中回调函数的概念 Promise 规范以及基本使用方式…

Await/Async 与 Promise

我经常会遇到这种问题:我想向后端POST几张图片,然后得到后端返回的文件名,这一步调用的函数是A函数。当所有图片都上传成功并且拿到文件名之后,再将文件名传给下一个调用的函数进行下一步处理,这一步调用的函数是B函数。我希望只需要用户触发一次就能按顺序执行这两个函数。然而,事与愿违,Javascript的函数调用似乎是同步的——执行A的同时,B也开始执行!这让我十分苦恼。 异步调用 后来我才了解到,其实Javascript是可以实现异步调用的,但是ES5中只能使用回调的方法实现异步,这将无法避免“回调地狱”的发生。于是,ECMA组织意识到这个问题,并在ES6中提出了Promise的概念。紧接着,ES7又基于Promise提出了async/await的概念。 引用一段对这个概念的评价: async/await是写异步代码的新方式,以前的方法有回调函数和Promise。 async/await是基于Promise实现的,它不能用于普通的回调函数。 async/await与Promise一样,是非阻塞的。 async/await使得异步代码看起来像同步代码,这正是它的魔力所在。 一个简单的例子 有一段这样的代码: async function test () { return 'hello world' } let result…

ECMAScript学习笔记-函数与变量

变量的声明 ECMAScript的变量是松散类型的。如下所示,使用var操作符定义一个名为“param”的新变量: var param; param变量可以被用来保存任何类型的数据。 var param1=1,param2="hello",param3=["w","o","r","l","d"]; 上例可以同时定义多个变量,并且每个变量被赋予不同类型的值是合法的。 函数的声明 ECMAScript定义函数使用function操作符: function MyFunc(param1,param2,...){ _BODY_ } 关于函数的书写 ECMAScript中定义的函数的函数体可以不用{}括起来,但是为了增强代码的美观性和可读性,同时为了避免犯不必要的错误,函数体最好用{}括起。 关于在函数体中声明的变量 通常,…

ECMAScript学习笔记-数据类型

数据类型 ECMAScript定义了5种基本类型:String、Number、Boolean、Undefined和Null;和1种复杂类型:Object。 5种基本类型分别对应着:字符串、数字、布尔值、未定义和空。 数据类型的探测 数据类型的探测一般采用typeof操作符,例如: var param="test"; console.log(typeof param);//控制台返回object var param=true; console.log(typeof param);//控制台返回boolean var param=123; console.log(typeof param);//控制台返回number 关于变量未被赋值的情况 var param; console.log(typeof param);//控制台返回object…