ES6回顾

变量

1.一、let和var

var a = [];
for (var i = 0; i < 10; i++) {
  a[i] = function () {
    console.log(i);
  };
}
a[6](); // 10

var a = [];
for (let i = 0; i < 10; i++) {
  a[i] = function () {
    console.log(i);
  };
}
a[6](); // 6
复制代码

上面代码中,变量i是var命令声明的,在全局范围内都有效,因此全局只有一个变量i。每一次循环,变量i的值都会发生改变,而循环内被赋给数组a的函数内部的console.log(i),里面的i指向的就是全局的i。也就是说,全部数组a的成员里面的i,指向的都是同一个i,致使运行时输出的是最后一轮的i的值,也就是 10。
若是使用let,声明的变量仅在块级做用域内有效,变量i是let声明的,当前的i只在本轮循环有效,因此每一次循环的i其实都是一个新的变量,因此最后输出的是6。你可能会问,若是每一轮循环的变量i都是从新声明的,那它怎么知道上一轮循环的值,从而计算出本轮循环的值?这是由于 JavaScript 引擎内部会记住上一轮循环的值,初始化本轮的变量i时,就在上一轮循环的基础上进行计算。es6

var tmp = 123;

if (true) {
  tmp = 'abc'; // ReferenceError
  let tmp;
}
复制代码

ES6 明确规定,若是区块中存在let和const命令,这个区块对这些命令声明的变量,从一开始就造成了封闭做用域。凡是在声明以前就使用这些变量,就会报错。
总之,在代码块内,使用let命令声明变量以前,该变量都是不可用的。这在语法上,称为“暂时性死区”(temporal dead zone,简称 TDZ)。算法

1.二、顶层对象属性

ES5 之中,顶层对象的属性与全局变量是等价的。
ES6 为了改变这一点,一方面规定,为了保持兼容性,var命令和function命令声明的全局变量,依旧是顶层对象的属性;另外一方面规定,let命令、const命令、class命令声明的全局变量,不属于顶层对象的属性。也就是说,从 ES6 开始,全局变量将逐步与顶层对象的属性脱钩。数组

同一段代码为了可以在各类环境,都能取到顶层对象,如今通常是使用this变量,可是有局限性。 全局环境中,this会返回顶层对象。可是,Node 模块和 ES6 模块中,this返回的是当前模块。数据结构

解构赋值

要想解构成功函数

  • 右边长度必须大于等于左边?
  • 右边必须是可遍历的,Iterator 结构 解构赋值容许指定默认值

字符串方法扩展

includes(), startsWith(), endsWith()
repeat()
padStart(),padEnd() 补全方法学习

函数的扩展

箭头函数有几个使用注意点。ui

(1)函数体内的this对象,就是定义时所在的对象,而不是使用时所在的对象。this

(2)不能够看成构造函数,也就是说,不可使用new命令,不然会抛出一个错误。spa

(3)不可使用arguments对象,该对象在函数体内不存在。若是要用,能够用 rest 参数代替。prototype

(4)不可使用yield命令,所以箭头函数不能用做 Generator 函数。

数组的扩展

Array.from方法用于将两类对象转为真正的数组:相似数组的对象(array-like object)和可遍历(iterable)的对象(包括 ES6 新增的数据结构 Set 和 Map)。

Array.of方法用于将一组值,转换为数组。

ES6 提供三个新的方法——entries(),keys()和values()——用于遍历数组。它们都返回一个遍历器对象,能够用for...of循环进行遍历,惟一的区别是keys()是对键名的遍历、values()是对键值的遍历,entries()是对键值对的遍历。

Array.prototype.includes方法返回一个布尔值,表示某个数组是否包含给定的值,与字符串的includes方法相似。

flat()默认只会“拉平”一层,若是想要“拉平”多层的嵌套数组,能够将flat()方法的参数写成一个整数,表示想要拉平的层数,默认为1

flatMap()方法对原数组的每一个成员执行一个函数(至关于执行Array.prototype.map()),而后对返回值组成的数组执行flat()方法。该方法返回一个新数组,不改变原数组

对象的扩展

this关键字老是指向函数所在的当前对象,ES6又新增了另外一个相似的关键字super,指向当前对象的原型对象

属性的赋值器(setter)和取值器(getter)

ES5 比较两个值是否相等,只有两个运算符:相等运算符(==)和严格相等运算符(===)。它们都有缺点,前者会自动转换数据类型,后者的NaN不等于自身,以及+0等于-0。Object.is就是部署这个算法的新方法。它用来比较两个值是否严格相等,与严格比较运算符(===)的行为基本一致。

Object.assign方法用于对象的合并,将源对象(source)的全部可枚举属性,复制到目标对象(target)。

Object.keys(),Object.values(),Object.entries() Object.fromEntries()方法是Object.entries()的逆操做,用于将一个键值对数组转为对象

Set和Map数据结构

Set函数能够接受一个数组(或者具备 iterable 接口的其余数据结构)做为参数,用来初始化。
向 Set 加入值的时候,不会发生类型转换,
在 Set 内部,两个NaN是相等。

Set和Map 结构的实例有四个遍历方法,能够用于遍历成员。

keys():返回键名的遍历器 values():返回键值的遍历器 entries():返回键值对的遍历器

复制代码

forEach():使用回调函数遍历每一个成员

Set 结构的实例默承认遍历,它的默认遍历器生成函数就是它的values方法。???

Set.prototype[Symbol.iterator] === Set.prototype.values
// true
复制代码

这意味着,能够省略values方法,直接用for...of循环遍历 Set。

let set = new Set(['red', 'green', 'blue']);

for (let x of set) {
  console.log(x);
}
// red
// green
// blue
复制代码

WeakSet 结构与 Set 相似,也是不重复的值的集合。可是,它与 Set 有两个区别。

首先,WeakSet 的成员只能是对象,而不能是其余类型的值。

其次,WeakSet 中的对象都是弱引用,即垃圾回收机制不考虑 WeakSet 对该对象的引用,也就是说,若是其余对象都再也不引用该对象,那么垃圾回收机制会自动回收该对象所占用的内存,不考虑该对象还存在于 WeakSet 之中。

WeakSet 的成员是不适合引用的,由于它会随时消失。另外,因为 WeakSet 内部有多少个成员,取决于垃圾回收机制有没有运行,运行先后极可能成员个数是不同的,而垃圾回收机制什么时候运行是不可预测的,所以 ES6 规定 WeakSet 不可遍历。

ES6 提供了 Map 数据结构。它相似于对象,也是键值对的集合,可是“键”的范围不限于字符串,各类类型的值(包括对象)均可以看成键。也就是说,Object 结构提供了“字符串—值”的对应,Map 结构提供了“值—值”的对应,是一种更完善的 Hash 结构实现。若是你须要“键值对”的数据结构,Map 比 Object 更合适。

Proxy

Proxy 能够理解成,在目标对象以前架设一层“拦截”,外界对该对象的访问,都必须先经过这层拦截,所以提供了一种机制,能够对外界的访问进行过滤和改写。

Proxy 实际上重载(overload)了点运算符,即用本身的定义覆盖了语言的原始定义。

学习资源来自阮一峰老师的ECMAScript 6 入门

相关文章
相关标签/搜索