参考阮一峰的ECMAScript 6 入门
扩展
字符串扩展
- 传统的写法相当繁琐不方便,ES6引入了模板字符串,用反引号(`)标识,可以在字符串中嵌入变量。
const Dell = { name: 'Dell', age: 23, getMsg1: function(){ console.log('Name:' + this.name + ',Age:' + this.age); }, getMsg2: function(){ // 在字符串中通过插值嵌入变量 console.log(`Name:${this.name},Age:${this.age}`); } } Dell.getMsg1(); Dell.getMsg2();
- 字符串对象的新增方法
1.includes(), startsWith(), endsWith()传统上,JavaScript 只有indexOf方法,可以用来确定一个字符串是否包含在另一个字符串中。indexOf() 方法返回指定的字符串值在字符串中首次出现的位置,对大小写敏感,如果要检索的字符串值没有出现,则该方法返回 -1。
ES6 又提供了三种新方法:var str ='Hello World'; if( str.indexOf('hello',0)!==-1){ console.log('存在'); }else{ console.log('不存在'); }// 输出: 不存在
includes():返回布尔值,表示是否找到了参数字符串。
startsWith():返回布尔值,表示参数字符串是否在原字符串的头部。
endsWith():返回布尔值,表示参数字符串是否在原字符串的尾部。
三个方法都支持第二个参数,表示开始搜索的位置。endsWith方法针对0~n个字符,而其他两个方法针对从第n个位置直到字符串结束。let s ='Hello world!'; s.startsWith('world',6)// true s.endsWith('Hello',5)// true s.includes('Hello',6)// false
2.repeat()
repeat方法返回一个新字符串,表示将原字符串重复n次。参数如果是小数,会被取整。
如果repeat的参数是负数或者Infinity,会报错。'hello'.repeat(2)// "hellohello" 'x'.repeat(2.9)// "xx" 'x'.repeat(2.2)// "xx"
但是,如果参数是 0 到 -1 之间的小数,则等同于 0,这是因为会先进行取整运算。0 到 -1之间的小数,取整以后等于 -0,repeat视同为 0。'na'.repeat(Infinity)// RangeError 'na'.repeat(-1) //引发RangeError
参数NaN等同于 0。'na'.repeat(-0.9)// ""
如果repeat的参数是字符串,则会先转换成数字。'na'.repeat(NaN)// ""
3.padStart()头部补全,padEnd()尾部补全'na'.repeat('na')// "" 'na'.repeat('3')// "nanana"
ES2017引入了字符串补全长度的功能。
如果某个字符串不够指定长度,会在头部或尾部补全。
上面代码中,padStart()和padEnd()一共接受两个参数:字符串补全生效的最大长度、用来补全的字符串。 如果原字符串的长度,等于或大于最大长度,则字符串补全不生效,返回原字符串。'x'.padStart(5,'ab')// 'ababx' 'x'.padEnd(5,'ab')// 'xabab'
如果用来补全的字符串与原字符串,两者的长度之和超过了最大长度,则会截去超出位数的补全字符串。'xxx'.padStart(2,'ab')// 'xxx'
另一个用途是提示字符串格式。'abc'.5(pathStart10,'0')// "0000123456"
'12'.padStart(10, 'YYYY-MM-DD') // "YYYY-MM-12" '09-12'.padStart(10,'YYYY-MM-DD')// "YYYY-09-12"
- for…of循环遍历。
for(let i of'foo'){ console.log(i); // "f"// "o"// "o" }
- Unicode表示法
Unicode是一项标准,包括字符集、编码方案等。它是为了解决传统的字符编码方案的局限而产生的,为每种语言中的每个字符设定了统一并且唯一的二进制编码,以满足跨平台、跨语言进行文本转换、处理的要求。
采用\uxxxx形式表示一个字符,只限于码点在\u0000~\uFFFF之间的字符,超出这个范围的字符,必须用两个双字节的形式表示。ES6中可以将码点放入大括号。"\u{41}\u{42}\u{43}"// "ABC"
数值扩展
1.二进制和八进制ES6 提供了二进制和八进制数值的新的写法,分别用前缀0b(或0B)和0o(或0O)表示。
0b111110111 === 503 // true
0o767 === 503 // true
可以使用Number方法将0b和0o前缀的字符串数值转为十进制。
Number('0b111') // 7
Number('0o10') // 8
2.Number.isFinite(), Number.isNaN()
ES6在Number对象上,新提供了Number.isFinite()和Number.isNaN()两个方法。
isFinite(25) // true
isFinite("25") // true
Number.isFinite(25) // true
Number.isFinite("25") // false
isNaN(NaN) // true
isNaN("NaN") // true
Number.isNaN(NaN) // true
它们与传统的全局方法isFinite()和isNaN()的区别在于,传统方法先调用Number()将非数值的值转为数值,再进行判断。
而这两个新方法只对数值有效,Number.isFinite()对于非数值一律返回false, Number.isNaN()只有对于NaN才返回true,非NaN一律返回false。
3.Number.parseInt(),Number.parseFloat()
// ES5的写法
parseInt('12.54')// 12
parseFloat('123.45')// 123.45
// ES6的写法
Number.parseInt('12.54') // 12
Number.parseFloat('123.45') // 123.45
函数扩展
1.默认参数
ES6之前,一般采用以下方法为函数的参数指定默认值:
function log(x, y) {
y = y || 'World';
console.log(x, y);
}
log('Hello') // Hello World
ES6 允许为函数的参数设置默认值,只有传入undefined才能触发该参数等于默认值,null则没有这个效果。
function foo(a,x = 5, y = 6) {
console.log(a, x, y);
}
foo(1, undefined, null)
// 1 5 null
2.箭头函数(=>)
如果箭头函数不需要参数或需要多个参数,就使用一个圆括号代表参数部分。可以使用大括号将它们括起来,但是,如果箭头函数直接返回一个对象,必须在对象外面加上括号。
// 函数名 | 函数参数 | 函数体
let getItem=(id,name)=>({id: id, name: name});
如果箭头函数只有一行语句,且不需要返回值,可以不用写大括号。
let fn = () => void a();
箭头函数的一个用处是简化回调函数。
// 正常函数写法
[1,2,3].map(function(x){return x * x;});
// 箭头函数写法
const result =[1,2,3].map(x => x * x);
console.log(result);// [1, 4, 9]
对象扩展
属性和方法简洁写法
var name = 'Dell';
var person = {
//等于同于name:name
name,
getName(){
console.log(name);
}
super关键字
this关键字总是指向函数所在的当前对象,ES6 新增了一个类似的关键字super,指向当前对象的原型对象。
super关键字表示原型对象时,只能用在对象的方法之中,用在其他地方都会报错。
const proto ={
x:'hello',
foo(){
console.log(this.x);
}
};
const obj ={
x:'world',
foo(){
super.foo();// 调用原型对象的foo方法
}
};
Object.setPrototypeOf(obj,proto);
obj.foo(); // “world”
Object.setPrototypeOf(),为现有对象设置原型,返回一个新对象。接收两个参数:现有对象、原型对象。
创建的两个对象都有相同名字的属性和方法,Object.setPrototypeOf(obj, proto)使得obj的原型对象为proto。
因为super指向当前对象的原型对象proto,所以super.foo指向原型对象proto的foo方法,但是绑定的this却还是当前对象obj,因此输出的就是world。
数组扩展
扩展运算符:
扩展运算符将一个数组,变为参数序列。
function fn(x,y,z){
console.log(x+y+z);
}
var arr = [1,2,3];
fn(...arr); // 6
// apply()方法
fn.apply(null,arr); // 6
新的方法:
1.Array.from()
只要是部署了 Iterator 接口的数据结构,Array.from都能将其转为数组。
把一个类似数组的对象转为真正的数组。
let arrayLike = {
'0': 'a',
'1': 'b',
length: 2
};
let arr2 = Array.from(arrayLike);
console.log(arr2);// ['a', 'b']
Array.from('hello')
// ['h', 'e', 'l', 'l', 'o']
2.Array.of()
Array.of方法用于将一组值,转换为数组。
Array.of(3, 11, 8) // [3,11,8]
3.Array.find() 和 Array.findIndex()
数组实例的find方法,用于找出第一个符合条件的数组成员。它的参数是一个回调函数,所有数组成员依次执行该回调函数,直到找出第一个返回值为true的成员,然后返回该成员。如果没有符合条件的成员,则返回undefined。
find方法的回调函数可以接受三个参数,依次为当前的值、当前的位置和原数组。
[1, 4, -5, 10].find((n) => n < 0)
// -5
[1, 5, 10, 15].find(function(value, index, arr) {
return value > 9;
}) // 10
数组实例的findIndex方法的用法与find方法非常类似,返回第一个符合条件的数组成员的位置,如果所有成员都不符合条件,则返回-1。
[1, 5, 10, 15].findIndex(function(value, index, arr) {
return value > 9;
}) // 2
这两个方法都可以接受第二个参数,用来绑定回调函数的this对象。
function f(v){
return v > this.age;
}
let person = {name: 'John', age: 20};
[10, 12, 26, 15].find(f, person); // 26
find函数接收了第二个参数person对象,回调函数中的this对象指向person对象。
4.Array.fill()
fill方法用于填充一个数组。
可以接受三个参数:给定值、用于指定填充的起始位置、结束位置。
new Array(3).fill(7)
// [7, 7, 7]
['a', 'b', 'c'].fill(7, 1, 2)
// ['a', 7, 'c']
5.keys(),values(),entries()
用于遍历数组。它们都返回一个遍历器对象,可以用for…of循环进行遍历,唯一的区别是keys()是对键名的遍历、values()是对键值的遍历,entries()是对键值对的遍历。
for (let [index, elem] of ['a', 'b'].entries()) {
console.log(index, elem);
}
// 0 "a"
// 1 "b"
6.Array.includes()
includes方法返回一个布尔值,表示某个数组是否包含给定的值,与字符串的includes方法类似。
该方法的二个参数:给定的值、搜索的起始位置(默认为0)
[1, 2, 3].includes(2) // true
[1, 2, NaN].includes(NaN) // true
[1, 2, 3].includes(3, 1); // true