ES6 (数值、数组、函数、对象的扩展)、类、module、set

145 阅读3分钟

数值的扩展

-指数运算符(**)

2 ** 2 // 4
2 ** 3 // 8

// 相当于 2 ** (3 ** 2)
2 ** 3 ** 2  // 512

函数扩展

  • 函数的参数制定默认值

ES6 之前,不能直接为函数的参数指定默认值,只能采用变通的方法。ES6允许为函数的参数设置默认值,即直接写在参数定义的后面。

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

log('Hello') // Hello World
log('Hello', 'China') // Hello China
  • rest参数

ES6 引入 rest 参数(形式为...变量名),用于获取函数的多余参数,这样就不需要使用arguments对象了。rest 参数搭配的变量是一个数组,该变量将多余的参数放入数组中。

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

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

  return sum;
}

add(2, 5, 3) // 10
  • name 属性

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

function foo() {}
foo.name // "foo"

JavaScript 语言中,生成实例对象的传统方法是通过构造函数。

function Point(x, y) {
  this.x = x;
  this.y = y;
}

Point.prototype.toString = function () {
  return '(' + this.x + ', ' + this.y + ')';
};

var p = new Point(1, 2);

ES6 提供了更接近传统语言的写法,引入了 Class(类)这个概念,作为对象的模板。通过class关键字,可以定义类。

class Point {
  constructor(x, y) {
    this.x = x;
    this.y = y;
  }

  toString() {
    return '(' + this.x + ', ' + this.y + ')';
  }
}

解析:可以看到里面有一个constructor方法,这就是构造方法,而this关键字则代表实例对象。

类的实例:

生成类的实例的写法,与 ES5 完全一样,也是使用new命令。

class Point(){
    
}

var point = new Point(2,3)

类的继承:

Class 可以通过extends关键字实现继承。

class Point {
}

class ColorPoint extends Point {
}

解析:定义了一个ColorPoint类,该类通过extends关键字,继承了Point类的所有属性和方法。但是由于没有部署任何代码,所以这两个类完全一样,等于复制了一个Point类。

class ColorPoint extends Point {
  constructor(x, y, color) {
    super(x, y); // 调用父类的constructor(x, y)
    this.color = color;
  }

  toString() {
    return this.color + ' ' + super.toString(); // 调用父类的toString()
  }
}

解析:constructor方法和toString方法之中,都出现了super关键字,它在这里表示父类的构造函数,用来新建父类的this对象。

子类必须在constructor方法中调用super方法,否则新建实例时会报错。这是因为子类自己的this对象,必须先通过父类的构造函数完成塑造,得到与父类同样的实例属性和方法,然后再对其进行加工,加上子类自己的实例属性和方法。如果不调用super方法,子类就得不到this对象。

module

ES6模块不是对象,而是通过export命令显式指定输出的代码,再通过import命令输入

export命令规定的是对外的接口,必须与模块内部的变量建立一一对应关系。

// 写法一
export var m = 1;

// 写法二
var m = 1;
export {m};

// 写法三
var n = 1;
export {n as m};  // export输出的是m,使用as关键字重命名

使用export命令定义了模块的对外接口以后,其他 JS 文件就可以通过import命令加载这个模块。

import {bar,point} from 'until'

为了给用户提供方便,让他们不用阅读文档就能加载模块,就要用到export default命令,为模块指定默认输出。

// 第一组
export default function crc32() { // 输出
  // ...
}

import crc32 from 'crc32'; // 输入

// 第二组
export function crc32() { // 输出
  // ...
};

import {crc32} from 'crc32'; // 输入

export default命令用于指定模块的默认输出。显然,一个模块只能有一个默认输出,因此export default命令只能使用一次。

module中的import的好处???

  • 按需加载
  • 条件加载
  • 动态的模块路径

ES6module加载规则??

浏览器加载 ES6 模块,也使用<script>标签,但是要加入type="module"属性。属于异步加载。

<script type="module" src="./foo.js"></script>

set

ES6 提供了新的数据结构 Set。它类似于数组,但是成员的值都是唯一的,没有重复的值。

// 去除数组的重复成员
[...new Set(array)]

// 去除字符串中重复的字符
[...new Set('ababbc')].join('')
// "abc"