# ES6

# Promise

# 基础使用

Promise意为允诺,虽然从现在开始努力(新建的Promise立即执行),但以后才能知道结局(成功或失败)。通常,Promise用于包装异步行为,即事件a完成后执行事件b,如果没有这种同步机制,就无法写出a->b的逻辑。

new Promise((resolve,reject)=>{
  setTimeout(()=>{console.log('after 1000ms')},1000);
  resolve();
})
//after 1000ms

MDN的图片清楚地介绍了Promise的过程

# Promise.prototype.then()

我们注意到Promise接受了一个函数,而这个函数接受了两个参数resolve和reject,这俩是内置的函数,触发它们可以改变Promise的状态(从pending到fulfillment或者rejection)。

状态改变会继续执行then方法中的函数:then接受两个函数,一个在resolve时触发,另一个在reject时触发。resolve或reject执行后,之后的代码仍然会执行并且先于then。

then支持链式调用,也就是说then的返回值仍然可以用then,无论返回原始值、抛出错误还是返回Promise最终都返回Promise,具体情况参考下表(很好理解,不用记)。

new Promise((resolve,reject)=>{
  if(Math.random()>0.5){
    resolve('suc');
  }else{
    reject('err');
  }
}).then((resolve)=>{
  console.log(resolve)
},(reject)=>{
  console.log(reject)
})

//可能输出suc或err

# Promise.prototype.catch()

如果Promise的状态变成reject,不仅会触发then 方法,也会触发catch方法。

从实现的角度上讲,该方法与使用then的第二个参数完全相同。

new Promise((resolve,reject)=>{
    reject('err');
}).catch((err)=>{
  console.log(err)
})

//err

# 关于throw

通常throw会触发then的第二个方法和catch。但在异步函数中调用throw无效(同步函数内有效),在resolved()触发后throw无效。

# Promise.all()

通常接受一个Promise数组,返回一个Promise,都完成时返回的Promise变fullfillment,有一个错误即变reject。如果打算在网页加载时显示loading,使用Promise.all响应图片的onload是个好主意。

实际上Promise.all接受所有的可迭代对象,如果传入的对象为空,返回fullfillment的Promise;如果对象不包含Promise,则返回异步完成的Promise(与前者的区别涉及Event-loop,对于异步完成的Promise,之后的同步代码会认为其处于pending状态);其他情况返回pending的Promise并根据执行情况转换状态。

# Promise.race()

和Promisel.all()相近,一旦其中一个Promise状态改变结果即确定(由最早改变状态的Promise决定)。用途可能在从不同路径请求相同资源,选择较快的那一个。

# Promise.resolve()

手动创建已经resolve的Promise。接受一个参数value,返回的Promise已执行resolve(value)。value如果是Promise,则直接返回此Promise;如果是带有then方法的对象let obj = {then:(res,rej)=>{res()}},返回的Promise相当于已执行了then方法new Promise(obj.then)

# thenable

指具有then方法的对象,可以作为参数传给Promise。

# Promise.reject()

手动创建已经reject的Promise。接受一个参数作为reject的原因(可以是Error对象)。

# Promise.prototype.allSettled()

还处于Draft。allSettled接受一个Promise数组,等待所有的Promise都被resolve或reject,它返回一个Promise,其中传递了每一个Promise的status。

# generator 生成器 ✏️

# 模板字符串/模板字面量

用反引号``表达的字符串,可以在其中使用${expression}表达式。以表达式开头的模板字符串被称为带标签的模板字符串(通常是函数)。

模板字符串支持多行字符串、表达式与嵌套(需要在表达式内)。

let total = 10;
let str = `She has ${total} apples.`
let str1 = `He said that ${`She has ${total} apples`}`

# 带标签的模板字符串

字符串前的函数接收了字符串与表达式,前者以数组的形式,后者以多个参数的形式传递,通过函数返回处理过后的值。

let dict=['一个顶俩','救过不给']
let harmony = function(str,exp1,exp2){
  if(exp1=="一个顶俩"){
    exp1="****"
  }
  if(exp2=="救过不给"){
    exp2="****"
  }
  return str[0]+exp1+exp2+str[2]
}
let str1 =harmony`我发送了两个红包${dict[0]}${dict[1]},请用新版QQ查看`
//str1
//我发送了两个红包********,请用新版QQ查看 :str数组有3个元素,str[1]=='' :str数组还有特殊的raw方法,可以获得未转义的字符串
//dict
//[ '一个顶俩', '救过不给' ] :不改变原表达式

# 类与对象

# 转译

# babel

# polypill

# traceur

# 遍历器 Iterator

Iterator提供了一个通用的接口,只要有此接口就可以用for(let item of obj)完成遍历。遍历器除了访问每一个成员,还决定访问的顺序。

# 解构赋值

在扩展运算符中,我们已经了解构赋值的用法。也许它应该叫模式匹配。

# 数组形式的解构赋值

let [a,b,c] = [1,2,3]
//a==1 b==2 c==3

let [d,[e,f],g] = [4,[5,6],7]
//d==4 e==5 f==6 g==7 不写f也不会报错

let [d,[e,f=10],g] = [4,[5],6]
//d==4 e==5 f==10 g==6 f等于默认值

右边的对象不具有Iterator接口会导致报错,而具有Iterator接口的对象(即使不是数组)不会报错。

# 对象形式的解构赋值

let {x,y} = {x:100,y:50};
//x==100 y==50

let {random} = Math;
let {log} = console;
//random==Math.random log==console.log

let {food:dinner} = {food:"pork"};
//dinner=="pork"

let {obj:{day,night}} = {obj:{day:'0',night:'12'}}
//day==0 night==12

let obj={};
Object.setPrototypeOf(obj,{size:67});
let {size} = obj;
//支持获取原型上的属性

let {xx=0,y:yy=83} ={}
//xx=0 yy=83 使用默认值

# 函数参数形式的解构赋值

在函数参数中,每一个参数都可以解构。

let f1=([a,b],[c])=>a+b+c;
f1([1,2],[3]);
//6

let f2=({a,b=10},{c=5}={})=>a+b+c;
f2({a:10});
//25

# 箭头函数

()=>

_=>

# 参考

TIP

# Promise.then()的返回值

当一个Promise完成(fulfilled)或者失败(rejected),返回函数将被异步调用(由当前的线程循环来调度完成)。具体的返回值依据以下规则返回:

  • 如果then中的回调函数返回一个值,那么then返回的Promise将会成为接受状态,并且将返回的值作为接受状态的回调函数的参数值。

  • 如果then中的回调函数没有返回值,那么then返回的Promise将会成为接受状态,并且该接受状态的回调函数的参数值为 undefined。

  • 如果then中的回调函数抛出一个错误,那么then返回的Promise将会成为拒绝状态,并且将抛出的错误作为拒绝状态的回调函数的参数值。

  • 如果then中的回调函数返回一个已经是接受状态的Promise,那么then返回的Promise也会成为接受状态,并且将那个Promise的接受状态的回调函数的参数值作为该被返回的Promise的接受状态回调函数的参数值。

  • 如果then中的回调函数返回一个已经是拒绝状态的Promise,那么then返回的Promise也会成为拒绝状态,并且将那个Promise的拒绝状态的回调函数的参数值作为该被返回的Promise的拒绝状态回调函数的参数值。

  • 如果then中的回调函数返回一个未定状态(pending)的Promise,那么then返回Promise的状态也是未定的,并且它的终态与那个Promise的终态相同;同时,它变为终态时调用的回调函数参数与那个Promise变为终态时的回调函数的参数是相同的。

最后更新: 9/6/2019, 1:47:07 PM