ECMAScript 6(ES6) 目前基本成为业界标准,它的普及速度比 ES5 要快很多,主要原因是现代浏览器对 ES6 的支持相当迅速,尤其是 Chrome 和 Firefox 浏览器,已经支持 ES6 中绝大多数的特性。

1.let 和 const


在ES6新特性中,增加的两个声明变量和常量的方法,let用于声明变量,const用于声明常量。

①在JS中是没有块级作用域的,而使用let就可以形成块级作用域:

{
 var a = 1; 
 let b = 2; 
} 
console.log(a); //1 
console.log(b); //not defined

②let不会像var那样发生变量提升:

console.log(a); // not defined
let a = 1;

③let不允许在相同块级作用域内,重复声明同一个变量:

//报错
{
 var a = 1;
 let a = 2;
}
// 报错
{
 let a = 1;
 let a = 2;
}

①const与let相同,只在所声明的块级作用域内有效。
②const与let相同,也不能在同一个块级作用域声明同一个变量。
③const用于声明常量,一旦声明 ,常量的值就不能改变。

2.箭头函数


在ES6新增的操作符 => ,用于简化函数的书写。

let f = function(){
 console.log("Hello Word!")
}
f( );
// 上述代码段可简写为:
let g = ()=>{
 console.log("Hello Word!")
}
g();
// 另外,若参数只有一个,()也可省略,若函数内只有一行语句,{}也可省略:
let a = 1;
let h = a => console.log(a);
h( );

需要注意的是:箭头函数没有绑定 this。

3.字符串模板


ES6中允许使用反引号 `` 来创建字符串,它可以当作普通字符串使用,也可以用来定义多行字符串,或者在字符串中使用${}嵌入变量。

最基础的用法:

let a = 18;
console.log(`我今年${a}岁了`) // 我今年18岁了

模板字符串还可以拼接和插入表达式:

let a = 18;
let b = 2;
console.log(`我今年${a + b}岁了`+`,`+`明年就会多一岁`+`。`); // 我今年20岁了,明年就会多一岁。

4.扩展运算符


扩展运算符用三个点号表示,功能是把数组或类数组对象展开成一系列用逗号隔开的值。

let arr = [1, 2, 3];
let arr2 = [...arr,4,5,6]
console.log(arr2); // 1,2,3,4,5,6

更深层次的用法:

let arr = [1, 2, 3];
//数组深拷贝
let arr2 = arr;
let arr3 = [...arr];
console.log(arr === arr2); //true, 说明arr和arr2指向同一个数组
console.log(arr === arr3); //false, 说明arr3和arr指向不同数组

//字符串转数组
let str = 'love';
let arr5 = [...str];
console.log(arr5); //[ 'l', 'o', 'v', 'e' ]

5.默认参数


ES6可以在定义函数的时候设置参数的默认值了。

function sayHello(name = "xiaoer") { 
 //如果没有传这个参数,才会有默认值,
 console.log(`Hello ${name}`);
}

sayHello(); //输出:Hello xiaoer
sayHello("wangcai"); //输出:Hello wangcai

6.解构赋值


若一个函数要返回多个值,常规的做法是返回一个对象,将每个值做为这个对象的属性返回。在ES6中,利用解构这一特性,可以直接返回一个数组,数组中的值会自动被解析到对应接收该值的变量中。

function f() {
 return [1, 2];
}
var [x, y] = f();
console.log('x:' + x + ', y:' + y); // x:1,y:2

不止函数的返回值可以使用解构赋值,数组、对象的赋值也可以使用解构赋值。

let arr = [10, 20, 30, 40];
// 数组解构
let [one, two] = arr;
console.log(one, two); //10 ,20

let obj = {
 name: 'xiaoer',
 age: 18
}
let {name,age,sex} = obj;
// 解构出来的属性,如果不存在,默认值为undefined
console.log( name, age, sex ); //xiaoer 18 undefined

7.数组方法的扩展


伪静态方法

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

let arrLike = {
 0: 10,
 1: 20,
 2: 30,
 length: 3
}
let arr = Array.from(arrLike);
console.log(arr); //[10, 20, 30]

②Array.of()
Array.of方法用于将一组值,转换为数组。
它弥补了使用new Array()构造数组的奇怪行为 。

let arr = new Array(3); // 原始方法,构建了一个有三个内容的空数组

let arr1 = Array.of(3);
let arr2 = Array.of(1, 2, 3);
let arr3 = Array.of();

console.log(arr1); //[3]
console.log(arr2); //[1, 2, 3]
console.log(arr3); //[]

数组操作

①内部拷贝copyWithin()

数组实例的copyWithin方法,在当前数组内部,将指定位置的成员复制到其他位置(会覆盖原有成员),然后返回当前数组。也就是说,使用这个方法,会修改当前数组。

let arr = [1, 2, 3, 4, 5, 6, 7, 8];
arr.copyWithin(1, 5, 8);
console.log(arr); //[1, 6, 7, 8, 5, 6, 7, 8]

第一个参数代表从这个位置开始替换,后两个参数代表要拷贝的起始位置和结束位置,不包含结束元素,左闭右开。可以使用负值代表倒数。

②查找find()与findIndex()

这两个原型方法都有一个回调函数作为参数,(回调函数的参数依次为元素、索引、数组引用),find()会返回第一个满足条件的元素,findIndex()会返回第一个满足条件的索引。

let arr = [10, 20, 30, 40, 50];
console.log(arr.find(function(value, index, arr){
 return value > 25;
}));// 30
console.log(arr.findIndex(function(value, index, arr){
 return value > 25;
}));// 2

③填充fill()

这个方法用于填充数组,会修改调用它的数组。

let arr = [1, 2, 3];
console.log(arr.fill(100)); //[100, 100, 100]

此外还可以指定填充的起始位置和终止位置,同样也是左开右闭。

let arr = [1, 2, 3, 4, 5];
console.log(arr.fill(100, 1, 4)); //[1, 100, 100, 100, 5]

④包含includes()

这个方法用于检测数组是否含有某个特定值,返回布尔值。

let arr = [1, 'a', true, null, NaN];
console.log(arr.includes(1)); //true
console.log(arr.includes('a')); //true
console.log(arr.includes(true)); //true
console.log(arr.includes(null)); //true
console.log(arr.includes(NaN)); //true
console.log(arr.includes(undefined)); //false
console.log(arr.includes()); //false

8.创建类


我们知道,javascript不像java是面向对象编程的语言,而只可以说是基于对象编程的语言。所以在js中,我们通常都是用function和prototype来模拟类这个概念。

但是现在有了es6,我们可以像java那样创建一个类了。

class NBAPlayer{
 constructor(name,age,height){
 this.name= name;
 this.age= age;
 this.height= height;
 }
 say(){
 console.log(`我是${this.name},我今年${this.age}岁,我身高${this.height}`)
 }
}
var p1 = new NBAPlayer("库里",30,191);
p1.say( ); // 我是库里,我今年30岁,我身高191

9.两种新的数据结构


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

var s = new Set();

// 通过add方法向Set结构中加入成员
[2, 3, 5, 4, 5, 2, 2].map(x => s.add(x))

for (i of s) { console.log(i) }
// 2 3 4 5 (表明set结构不会添加重复的值)

console.log(Array.isArray(s)); 
// false 表明 set 并不是真正的数组,而是一个伪数组

而Map类似于对象,也是键值对集合,但是”键”的范围不限于字符串,对象也可以当作键。

var m = new Map();
obj = {p: "hello world"};

m.set(obj, "content");
console.log( m.get(obj) ); // content

在上面的代码中,将对象obj当作m的一个键。

var map = new Map([["name", "小明"], ["title", "Author"]]);

map.size //2
map.has("name"); //true
map.get("name"); //小明
map.has("title"); //true
map.get("title"); //Author

Map还可以接收一个数组进行初始化。

10.字符串扩展


repeat

ES6为字符串添加了一个 repeat() 方法,它接受一个参数作为字符串的重复次数,返回一个将初始字符串重复指定次数的新字符串。

console.log("x".repeat(3)); // "xxx"
console.log("hello".repeat(2)); // "hellohello"
console.log("abc".repeat(4)); // "abcabcabcabc"

trim

用于除去字符串中的空格。trim把左右的空格都除去,trimLeft除去左空格,trimRight除去右空格。

let str = " ab cd ";
str.trim(); // "ab cd"
str.trimLeft(); // "ab cd "
str.trimRight(); // " ab cd"

includes

该方法用于检测在字符串中是否存在所找的字符串,存在返回 true ,否则返回false

let str = "abcd";
str.includes("a"); // true
str.includes("z"); // false

strartsWith

判断指定的子字符串是否出现在目标字符串的开头位置。第二个参数选填,表示开始搜索的位置。

let str = "abcd";
str.startsWith("a"); // true
str.startsWith("b"); // false
str.startsWith("b",2); // true,从第二个字符开始

endsWidth

判断子字符串是否出现在目标字符串的尾部位置。第二个参数选填,表示针对前N个字符。

let str = "abcd";
str.endsWith("d"); // true
str.endsWith("c"); // false
str.endsWith("c",3); // true,针对前三个字符

padStart

ES6 引入的字符串补全长度的功能。如果某个字符串不够指定长度,会在头部补全。
一共接受两个参数,第一个参数用来指定字符串的最小长度,第二个参数是用来补全字符串。

'x'.padStart(5, 'ab') // 'ababx'
'x'.padStart(4, 'ab') // 'abax'

padEnd

ES6 引入的字符串补全长度的功能。如果某个字符串不够指定长度,会在尾部补全。
一共接受两个参数,第一个参数用来指定字符串的最小长度,第二个参数是用来补全字符串。

'x'.padEnd(5, 'ab') // 'xabab'
'x'.padEnd(4, 'ab') // 'xaba'

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

ES6新增特性