ES2015/ES2016/ES2017/ES2018/ES2019

# 一、前言
ES6是ECMA为JavaScript制定的第6个标准版本- 标准委员会最终决定,标准在每年6月正式发布并作为当年的正式版本,接下来的时间里就在此版本的基础上进行改动,直到下一年6月草案就自然变成新一年的版本,这样一来就无需以前的版本号,只要用年份标记即可。
ECMAscript 2015是在2015年6月发布ES6的第一个版本。以此类推,ECMAscript2016是ES6的第二个版本、 ECMAscript 2017是ES6的第三个版本。ES6既是一个历史名词也是一个泛指,含义是5.1版本以后的JavaScript下一代标准,目前涵盖了ES2015、ES2016、ES2017、ES2018、ES2019
所以有些文章上提到的ES7(实质上是ES2016)、ES8(实质上是ES2017)、ES9(实质上是ES2018)、ES10(实质上是ES2019),实质上都是一些不规范的概念。从ES1到ES6,每个标准都是花了好几年甚至十多年才制定下来,你一个ES6到ES7,ES7到ES8,才用了一年,按照这样的定义下去,那不是很快就ES20了。用正确的概念来说ES6目前涵盖了ES2015、ES2016、ES2017、ES2018、ES2019

# 二、ES2015

# 声明
const命令:声明常量let命令:声明变量
作用
作用域
- 全局作用域
- 函数作用域:
function() {} - 块级作用域:
{}
作用范围
var命令在全局代码中执行const命令和let命令只能在代码块中执行
赋值使用
const命令声明常量后必须立马赋值let命令声明变量后可立马赋值或使用时赋值
声明方法:
var、const、let、function、class、import
重点难点
- 不允许重复声明
- 未定义就使用会报错:
const命令和let命令不存在变量提升 - 暂时性死区:在代码块内使用let命令声明变量之前,该变量都不可用
# 解构赋值
- 字符串解构:
const [a, b, c, d, e] = "hello" - 数值解构:
const { toString: s } = 123 - 布尔值解构:
const { toString: b } = true
对象解构
- 形式:
const { x, y } = { x: 1, y: 2 } - 默认:
const { x, y = 2 } = { x: 1 } - 改名:
const { x, y: z } = { x: 1, y: 2 }
数组解构
- 规则:数据结构具有
Iterator接口可采用数组形式的解构赋值 - 形式:
const [x, y] = [1, 2] - 默认:
const [x, y = 2] = [1]
函数参数解构
- 数组解构:
function Func([x = 0, y = 1]) {} - 对象解构:
function Func({ x = 0, y = 1 } = {}) {}
应用场景
- 交换变量值:
[x, y] = [y, x] - 返回函数多个值:
const [x, y, z] = Func() - 定义函数参数:
Func([1, 2]) - 提取JSON数据:
const { name, version } = packageJson - 定义函数参数默认值:
function Func({ x = 1, y = 2 } = {}) {} - 遍历Map结构:
for (let [k, v] of Map) {} - 输入模块指定属性和方法:
const { readFile, writeFile } = require("fs")
重点难点
- 匹配模式:只要等号两边的模式相同,左边的变量就会被赋予对应的值
- 解构赋值规则:只要等号右边的值不是对象或数组,就先将其转为对象
- 解构默认值生效条件:属性值严格等于undefined
- 解构遵循匹配模式
- 解构不成功时变量的值等于
undefined undefined和null无法转为对象,因此无法进行解构
# 字符串扩展
Unicode表示法:大括号包含表示Unicode字符(\u{0xXX}或\u{0XXX})- 字符串遍历:可通过for-of遍历字符串
- 字符串模板:可单行可多行可插入变量的增强版字符串
- 标签模板:函数参数的特殊调用
String.raw():返回把字符串所有变量替换且对斜杠进行转义的结果String.fromCodePoint():返回码点对应字符codePointAt():返回字符对应码点(String.fromCodePoint()的逆操作)normalize():把字符的不同表示方法统一为同样形式,返回新字符串(Unicode正规化)repeat():把字符串重复n次,返回新字符串matchAll():返回正则表达式在字符串的所有匹配includes():是否存在指定字符串startsWith():是否存在字符串头部指定字符串endsWith():是否存在字符串尾部指定字符串
重点难点
以上扩展方法均可作用于由4个字节储存的
Unicode字符上
# 数值扩展
- 二进制表示法:0b或0B开头表示二进制(
0bXX或0BXX) - 八进制表示法:0o或0O开头表示二进制(
0oXX或0OXX) Number.EPSILON:数值最小精度Number.MIN_SAFE_INTEGER:最小安全数值(-2^53)Number.MAX_SAFE_INTEGER:最大安全数值(2^53)Number.parseInt():返回转换值的整数部分Number.parseFloat():返回转换值的浮点数部分Number.isFinite():是否为有限数值Number.isNaN():是否为NaNNumber.isInteger():是否为整数Number.isSafeInteger():是否在数值安全范围内Math.trunc():返回数值整数部分Math.sign():返回数值类型(正数1、负数-1、零0)Math.cbrt():返回数值立方根Math.clz32():返回数值的32位无符号整数形式Math.imul():返回两个数值相乘Math.fround():返回数值的32位单精度浮点数形式Math.hypot():返回所有数值平方和的平方根Math.expm1():返回e^n - 1Math.log1p():返回1 + n的自然对数(Math.log(1 + n))Math.log10():返回以10为底的n的对数Math.log2():返回以2为底的n的对数Math.sinh():返回n的双曲正弦Math.cosh():返回n的双曲余弦Math.tanh():返回n的双曲正切Math.asinh():返回n的反双曲正弦Math.acosh():返回n的反双曲余弦Math.atanh():返回n的反双曲正切
# 对象扩展
- 简洁表示法:直接写入变量和函数作为对象的属性和方法
({ prop, method() {} }) - 属性名表达式:字面量定义对象时使用[]定义键(
[prop],不能与上同时使用) - 方法的name属性:返回方法函数名
- 取值函数(
getter)和存值函数(setter):get/set函数名(属性的描述对象在get和set上) bind返回的函数:bound函数名Function构造函数返回的函数实例:anonymous
- 取值函数(
- 属性的可枚举性和遍历:描述对象的
enumerable super关键字:指向当前对象的原型对象(只能用在对象的简写方法中method() {})Object.is():对比两值是否相等Object.assign():合并对象(浅拷贝),返回原对象Object.getPrototypeOf():返回对象的原型对象Object.setPrototypeOf():设置对象的原型对象__proto__:返回或设置对象的原型对象
属性遍历
- 描述:自身、可继承、可枚举、非枚举、
Symbol - 遍历
for-in:遍历对象自身可继承可枚举属性Object.keys():返回对象自身可枚举属性的键组成的数组Object.getOwnPropertyNames():返回对象自身可继承可枚举非枚举属性的键组成的数组Object.getOwnPropertySymbols():返回对象Symbol属性的键组成的数组Reflect.ownKeys():返回对象自身可继承可枚举非枚举Symbol属性的键组成的数组
- 规则
- 首先遍历所有数值键,按照数值升序排列
- 其次遍历所有字符串键,按照加入时间升序排列
- 最后遍历所有
Symbol键,按照加入时间升序排列
# 数组扩展
- 扩展运算符(
...):转换数组为用逗号分隔的参数序列([...arr],相当于rest/spread参数的逆运算) Array.from():转换具有Iterator接口的数据结构为真正数组,返回新数组- 类数组对象:包含
length的对象、Arguments对象、NodeList对象 - 可遍历对象:
String、Set结构、Map结构、Generator函数
- 类数组对象:包含
Array.of():转换一组值为真正数组,返回新数组copyWithin():把指定位置的成员复制到其他位置,返回原数组find():返回第一个符合条件的成员findIndex():返回第一个符合条件的成员索引值fill():根据指定值填充整个数组,返回原数组keys():返回以索引值为遍历器的对象values():返回以属性值为遍历器的对象entries():返回以索引值和属性值为遍历器的对象- 数组空位:ES6明确将数组空位转为
undefined(空位处理规不一,建议避免出现)
扩展应用
- 克隆数组:
const arr = [...arr1] - 合并数组:
const arr = [...arr1, ...arr2] - 拼接数组:
arr.push(...arr1) - 代替
apply:Math.max.apply(null, [x, y]) => Math.max(...[x, y]) - 转换字符串为数组:
[..."hello"] - 转换类数组对象为数组:
[...Arguments, ...NodeList] - 转换可遍历对象为数组:
[...String, ...Set, ...Map, ...Generator] - 与数组解构赋值结合:
const [x, ...rest/spread] = [1, 2, 3] - 计算
Unicode字符长度:Array.from("hello").length => [..."hello"].length
重点难点
- 使用
keys()、values()、entries()返回的遍历器对象,可用for-of自动遍历或next()手动遍历
# 函数扩展
箭头函数误区
- 函数体内的
this是定义时所在的对象而不是使用时所在的对象 - 可让
this指向固定化,这种特性很有利于封装回调函数 - 不可当作构造函数,因此箭头函数不可使用
new命令 - 不可使用
yield命令,因此箭头函数不能用作Generator函数 - 不可使用
Arguments对象,此对象在函数体内不存在(可用rest/spread参数代替) - 返回对象时必须在对象外面加上括号
# 正则扩展
- 变更
RegExp构造函数入参:允许首参数为正则对象,尾参数为正则修饰符(返回的正则表达式会忽略原正则表达式的修饰符) - 正则方法调用变更:字符串对象的
match()、replace()、search()、split()内部调用转为调用RegExp实例对应的RegExp.prototype[Symbol.方法] - u修饰符:
Unicode模式修饰符,正确处理大于\uFFFF的Unicode字符- 点字符(
.) Unicode表示法- 量词
- 预定义模式
i修饰符- 转义
- 点字符(
- y修饰符:粘连修饰符,确保匹配必须从剩余的第一个位置开始全局匹配(与g修饰符作用类似)
- unicode:是否设置
u修饰符 - sticky:是否设置
y修饰符 - flags:正则表达式的修饰符
重点难点
# Symbol
方法
内置
数据类型
应用场景
重点难点
# Set
Set