【阅读笔记】本文内容均来自:ECMAScript 6 入门
变量
let
- 不存在变量提升
- 暂时性死区
- 不允许重复声明
- 与顶层对象的属性脱钩
let a = 1
不会挂到window
上
块级作用域
- ES5 只有全局作用域和函数作用域
- ES6 允许块级作用域的任意嵌套
- 块级作用域的出现,实际上使得获得广泛应用的立即执行函数表达式(IIFE)不再必要了
- ES6 明确允许在块级作用域之中声明函数,但在浏览器的ES6实现中仍把块级作用域的函数声明当作
var
处理,建议写成函数表达式。
const
- 只在声明所在的块级作用域内有效,特性同
let
- const 声明变量时必须复制,以后不能赋值
- const 实际上保证的,并不是变量的值不得改动,而是变量指向的那个内存地址不得改动。
- 对于基础数据类型,const 指向的就是其值;而对于对象类型,const 指向其引用地址,对象的地址不可改变,但对象本身的属性值仍可以改。
- 如果必须将对象冻结(地址和值都不能改),应该使用
Object.freeze
解构赋值
数组解构形式
1 | let [x, y, ...z] = ['a']; |
- 只要某种数据结构具有 Iterator 接口,都可以采用数组形式的解构赋值。
1 | function* fibs() { |
- 解构赋值允许指定默认值,默认值生效的条件是:数组成员的值严格等于
undefined
1 | let [x = 1] = [undefined]; |
对象解构形式
1 | let { foo: baz } = { foo: "aaa", bar: "bbb" }; |
- 默认值生效的条件是:对象的属性值严格等于
undefined
1 | var {x = 3} = {x: undefined}; |
如果要将一个已经声明的变量用于解构赋值,必须非常小心。因为 JavaScript 引擎会将
{x}
理解成一个代码块,从而发生语法错误。解构赋值的规则是,只要等号右边的值不是对象或数组,就先将其转为对象。由于
undefined
和null
无法转为对象,所以对它们进行解构赋值,都会报错。常用场景:
let { log, sin, cos } = Math;
函数参数的解构赋值
1 | [[1, 2], [3, 4]].map(([a, b]) => a + b); |
变量解构赋值的用途
- 提取对象数据(或用于遍历数据结构)
- 函数参数的映射及默认值
- 输入模块的指定方法
字符串的扩展
ES6为字符串添加了
Iterator
接口,使得字符串可以被for...of
循环遍历。新增:
includes()
,startsWith()
,endsWith()
,repeat()
模板字符串
- 模板字符串中嵌入变量,需要将变量名写在
${}
之中。 - 大括号内部可以放入任意的JavaScript表达式,可以进行运算,以及引用对象属性。
- 模板字符串之中还能调用函数
高级用法
1 | const tmplFn = addrs => ` |
模板编译
1 | var template = ` |
正则的扩展
以下非 es6 新增
正则表达式中,点.
是一个特殊字符,代表任意的单个字符,但是行终止符(line terminator character)除外。以下四个字符属于”行终止符“:
- U+000A 换行符
\n
- U+000D 回车符
\r
- U+2028 行分隔符(line separator)
- U+2029 段分隔符(paragraph separator)
但是,很多时候我们希望匹配的是任意单个字符,有一种变通的写法[^]
数值的扩展
新增
- Number.isFinite()
- Number.isNaN()
- Number.parseInt()
- Number.parseFloat()
- Number.isInteger()
- Number.EPSILON
2.220446049250313e-16
- Number.isSafeInteger()
-2^53 ~ 2^53
函数的扩展
函数参数的默认值
- 参数变量是默认声明的,所以不能用
let
或const
再次声明。 - 参数默认值不是传值的,而是每次都重新计算默认值表达式的值。
- 也就是说,参数默认值是惰性求值的。
1 | let x = 99; |
rest 参数
rest 参数搭配的变量是一个数组,该变量将多余的参数放入数组中。
1 | // arguments变量的写法 |
注意
- rest 参数之后不能再有其他参数(即只能是最后一个参数),否则会报错。
- 函数的
length
属性,不包括 rest 参数。
箭头函数
- 函数体内的
this
对象,就是定义时所在的对象,而不是使用时所在的对象。 - 不可以当作构造函数,也就是说,不可以使用
new
命令,否则会抛出一个错误。 - 不可以使用
arguments
对象,该对象在函数体内不存在。如果要用,可以用 rest 参数代替。 - 不可以使用
yield
命令,因此箭头函数不能用作 Generator 函数。(但是箭头可以作为async
函数)
1 | function foo() { |
注意:由于箭头函数没有自己的this
,所以当然也就不能用call()
、apply()
、bind()
这些方法去改变this
的指向。