← 返回博客列表

ES6学习笔记

Vic.Wang2017/06/21883 阅读0 喜欢最近更新 2026/07/09 15:22:59

本文写于 2017 年,距今已有 9 年,文中提及的技术方案与接口可能已经过时,请注意甄别参考。

之前看过几遍阮一峰的《ECMAScript 6 入门》,但是不经常用,看了就忘。

这次看的时候决定好好记些笔记,方便日后翻看。

ES6声明变量的六种方法:

  • var
  • function
  • let
  • const
  • import
  • class

ES5只有两种声明变量的方法:var 和 function 命令。

let:声明变量

let a = 'Vic';
  • let 声明的变量只在代码块中有效
  • 变量声明后使用,不然报错
  • let 不存在变量提升
  • 处于暂时性死区的变量,用 typeof 会报错
  • 在同一代码块中,let 不允许重复声明变量

外部有同名变量,代码块内 let 又声明了该同名变量,则该变量在声明前不可被赋值,必须先声明后使用。

在用 let 声明变量之前使用该变量,从使用到声明这中间的过程就叫暂时性死区,会报错。

块级作用域

{
    let a = 'Vic';
    let f = function () {
        retuan a;
    }
}
  • 不同代码块,声明的同名变量不受影响
  • 块级作用域可以任意嵌套
  • let 声明的变量,外层作用域无法读取内层作用域
  • 块级作用域中可以声明函数,但当前作用域外无法使用
  • 块级作用域声明函数,存在兼容问题,应使用函数表达式

const: 声明只读常量

const PI = 3.1415;
  • const 声明的常量是只读的,一旦声明就不能改变
  • const 声明的常量,声明时必须赋值
  • 只在声明所在的块级作用域中有效
  • const 不存在常量提升
  • const 也有暂时性死区
  • 在同一代码块中,const 也不可重复声明
  • 不可赋值给其他变量
  • 声明的变量是个对象或数组,可修改但不可赋值

顶层对象的属性

顶层对象,在浏览器环境指的是 window 对象,在 Node 指的是 global 对象。

ES5 之中,顶层对象的属性与全局变量是等价的。

var 命令和 function 命令声明的全局变量,依旧是顶层对象的属性。

let 命令、const 命令、class 命令声明的全局变量,不属于顶层对象的属性。

变量的解构赋值

ES6 允许按照一定模式,从数组和对象中提取值,对变量进行赋值,这被成为解构。

1、数组的解构赋值

  • 模式匹配,只要等号两边的模式相同,左边的变量就会被赋予对应的值。
  • 不完全匹配,等号左边的模式,只匹配一部分等号右边的数组。
  • 解构不成功,变量的值等于 undefined。
  • 等号右边不是数组(严格地说不是可遍历的结构)将会报错。
  • Set 结构,也可以使用数组的解构赋值。
  • 解构赋值允许指定默认值。

1.1 模式匹配

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

let [foo, [[bar], baz]] = [1, [[2], 3]];
foo //1
bar //2
baz //3

let [ , , third] = ['foo', 'bar', 'baz'];
third //'baz'

let [x, , y] = [1, 2, 3];
x //1
y //3

let [head, ...tail] = [1, 2, 3, 4];
head //1
tail //[2, 3, 4]

let [x, y, ...z] = ['a'];
x //'a'
y //undefined
z //[]

1.2 解构不成功

let [foo] = [];
foo //undefined

let [bar, foo] = [1];
foo //undefined

1.3 不完全匹配

let [x, y] = [1, 2, 3];
x //1
y //2

let [a, [b], d] = [1, [2, 3], 4];
a //1
b //2
d //4

1.4 指定默认值

let [foo = true] = [];
foo //true

let [x = 1] = [undefined];
x //1

let [x = 1] = [null];
x //null

注意,ES6 内部使用严格相等运算符(===),判断一个位置是否有值。所以,如果一个数组成员不严格等于 undefined,默认值是不会生效的。

2、对象的解构赋值

解构不仅可以用于数组,还可以用于对象。

对象的解构与数组有一个重要的不同。数组的元素是按次序排列的,变量的取值由它的位置决定;而对象的属性没有次序,变量必须与属性同名,才能取到正确的值。

let { foo, bar } = { foo: 'aaa', bar: 'bbb' };
foo //'aaa'
bar //'bbb'

let { bar, foo } = { foo: 'aaa', bar: 'bbb' };
foo //'aaa'
bar //'bbb'

let { baz } = { foo: 'aaa', bar: 'bbb' };
baz //undefined

对象的解构指定默认值

var {x = 3} = {};
x //3

var {x, y = 5} = {x: 1};
x //1
y //5

3、字符串的解构赋值

字符串也可以解构赋值。这是因为此时,字符串被转换成了一个类似数组的对象。

const [a, b, c, d, e] = 'hello';
a //'h'
b //'e'
c //'l'
d //'l'
e //'o'

let {length : len} = 'hello';
len //5

4、数值和布尔值的解构赋值

解构赋值的规则是,只要等号右边的值不是对象或数组,就先将其转为对象。由于 undefined 和 null 无法转为对象,所以对它们进行解构赋值,都会报错。

5、函数参数的解构赋值

function add([x, y]) {
    return x + y;
}
add([1, 2]); //3

字符串的扩展

  • includes():返回布尔值,表示是否找到该字符串
  • startsWith():返回布尔值,表示字符串是否在源字符串头部
  • endsWith():返回布尔值,表示字符串是否在源字符串尾部
var s = 'mingsixue';
s.includes('ing'); //true
s.startsWith('ming'); //true
s.endsWith('xue'); //true

这三个方法都支持第二个参数,表示开始搜索的位置。

使用第二个参数n时,endsWith 的行为和其他两个方法有所不同,它针对前 n 个字符,而其他两个方法针对从第 n 个位置直到字符串结束。

  • repeat()方法返回一个新字符串,表示将原字符串重复n次。
'x'.repeat(3); //'xxx'
'vic'.repeat(2); //'vicvic'
  • padStart():在头部补全指定的字符串长度
  • padEnd():在尾部补全指定的字符串长度
'Vic'.padStart(7, 'love'); //loveVic
'love'.padEnd(7, 'Vic'); //loveVic

接受 2 个参数,第一个参数用来指定字符串的最小长度,第二个参数时用来补全的字符串。

如果原字符串的长度,等于或大于指定的最小长度,则返回原字符串。

如果用来补全的字符串与原字符串,两者的长度之和超过了指定的最小长度,则会截去超出位数的补全字符串。

如果省略第二个参数,默认使用空格补全长度。

模板字符串

模板字符串用反引号(`)标识,可以当作普通字符串使用,也可以用来定义多行字符串,或者在字符串中嵌入变量。

模板字符串中嵌入变量,需要将变量名写在 ${} 之中。

大括号内部可以放入任意的 JavaScript 表达式,可以进行运算,以及引用对象属性,还可以调用函数。

var name = 'vic';
`Hello ${name}`;

正则的扩展:

u 修饰符

ES6 对正则表达式添加了 u 修饰符,含义为 “Unicode模式”,用来正确处理大于 \uFFFF 的 Unicode 字符,也就是说,会正确处理四个字节的 UTF-16 编码。

u 修饰符的影响

  • 点字符(.),对于码点大于 0xFFFF 的 Unicode 字符,点字符不能识别,必须加上 u 修饰符。
  • 新增大括号表示 Unicode 字符,这种表示法在正则表达式中必须加上 u 修饰符,才能识别当中的大括号,否则被解读为量词。
  • 使用 u 修饰符后,所有量词都会正确识别码点大于 0xFFFF 的 Unicode 字符
  • 也影响预定义模式,能否正确识别码点大于 0xFFFF 的 Unicode 字符

y 修饰符

新增 y 修饰符,作用与 g 修饰符类似,都是全局匹配,后一次匹配都从上一次匹配成功的下一个位置开始。不同之处在于,g 修饰符只要剩余位置中存在匹配即可,而 y 修饰符确保匹配必须从剩余的第一个位置开始,这也就是“粘连”的涵义。

sticky 属性

与 y 修饰符相匹配,ES6 的正则对象多了 sticky 属性,表示是否设置了 y 修饰符

var r - /hello\d/y;
r.sticky; //true

flags 属性

ES6 为正则表达式新增了 flags 属性,会返回正则表达式的修饰符。

/abc/ig.flags;  //'gi'

数值的扩展:

isFinite()方法

ES6 在 Number 对象上,新提供了 Number.isFinite() 方法,用来检查一个数值是否为有限的(finite)。

Number.isFinite(15); //true
Number.isFinite(0.8); //true
Number.isFinite(NaN); //false
Number.isFinite(Infinity); //false
Number.isFinite(-Infinity); //false
Number.isFinite('foo'); //false
Number.isFinite('15'); //false
Number.isFinite(true); //false

isNaN()方法

Number.isNaN() 用来检查一个值是否为 NaN。

Number.isNaN(NaN); //true
Number.isNaN(15); //false
Number.isNaN('15'); //false
Number.isNaN(true); //false
Number.isNaN(9/NaN); //true
Number.isNaN('true'/0); //true
Number.isNaN('true'/'true'); //true

它们与传统的全局方法 isFinite() 和 isNaN() 的区别在于,传统方法先调用 Number() 将非数值的值转为数值,再进行判断,而这两个新方法只对数值有效,Number.isFinite()对于非数值一律返回 false, Number.isNaN() 只有对于 NaN 才返回 true,非 NaN 一律返回 false。

isFinite(25) // true
isFinite("25") // true
Number.isFinite(25) // true
Number.isFinite("25") // false

isNaN(NaN) // true
isNaN("NaN") // true
Number.isNaN(NaN) // true
Number.isNaN("NaN") // false
Number.isNaN(1) // false

isInteger()方法

Number.isInteger() 用来判断一个值是否为整数。需要注意的是,在 JavaScript 内部,整数和浮点数是同样的储存方法,所以 3 和 3.0 被视为同一个值。

Number.isInteger(25) // true
Number.isInteger(25.0) // true
Number.isInteger(25.1) // false
Number.isInteger("15") // false
Number.isInteger(true) // false

Math对象的扩展

Math.trunc()

Math.trunc 方法用于去除一个数的小数部分,返回整数部分。

对于非数值,Math.trunc 内部使用 Number 方法将其先转为数值。

对于空值和无法截取整数的值,返回 NaN。

Math.trunc(4.1) // 4
Math.trunc(4.9) // 4
Math.trunc(-4.1) // -4
Math.trunc(-4.9) // -4
Math.trunc(-0.1234) // -0

Math.trunc('123.456'); // 123

Math.trunc(NaN); // NaN
Math.trunc('foo'); // NaN
Math.trunc(); // NaN

Math.sign()

Math.sign 方法用来判断一个数到底是正数、负数、还是零。对于非数值,会先将其转换为数值。

它会返回五种值:

  • 参数为正数,返回 +1
  • 参数为负数,返回 -1
  • 参数为 0,返回 0
  • 参数为 -0,返回 -0
  • 其他值,返回 NaN
Math.sign(-5) // -1
Math.sign(5) // +1
Math.sign(0) // +0
Math.sign(-0) // -0
Math.sign(NaN) // NaN
Math.sign('9'); // +1
Math.sign('foo'); // NaN
Math.sign(); // NaN

函数的扩展

函数参数的默认值

ES6 允许为函数的参数设置默认值,即直接写在参数定义的后面。

function log(x, y = 'World') {
    console.log(x, y);
}

参数变量是默认声明的,所以不能用 let 或 const 再次声明。

rest参数

ES6 引入了 rest 参数(形式为...变量名),用于获取函数得多余参数。rest 参数搭配得变量是一个数组,将多余的参数放入数组中。

rest 参数之后不能再有其他参数(即只能是最后一个参数),否则会报错。

function add(...values) {
    let sum = 0;

    for (var val of values) {
        sum += val;
    }

    return sum;
}

add(2, 5, 3); //10

name属性

函数的 name 属性,返回该函数的函数名。

箭头函数

ES6 允许使用“箭头”( => )定义函数。

var f = v => v;

//上面的箭头函数等同于:

var f = function(v) {
    return v;
}

如果箭头函数不需要参数或需要多个参数,就使用一个圆括号代表参数部分。

var f = () => 5;
//等同于
var f = function () { return 5; };

var sum = (num1, num2) => num1 + num2;
//等同于
var sum = function(num1, num2) {
    return num1 + num2;
}

如果箭头函数的代码块部分多于一条语句,就要使用大括号将它们括起来,并且使用 return 语句返回。

var sum = (num1, num2) => { return num1 + num2; }


若有共鸣,不妨点个喜欢

本文地址:https://www.mingsixue.com/blog/detail/es6-study-notes

分享:微博QQ空间X