ECMAScript2016,2017和2018所有新功能的介绍与示例

前言

有时我们很难跟踪JavaScript(ECMScript)中的一些新特性,找到有用的代码示例更加困难。所以这篇文章主要介绍ES2016,ES2017,ES2018中的一些新特性与相关的示例代码,希望对你有所帮助。

ECMAScript 2016

1.Array.prototype.includes

includes 是Array上的一个简单实例方法,有助于轻松查找项是否在数组中(包括NaN 与indexOf不同)。

1.png

2.幂运算符
加法和减法等数学运算有像+和-这样的运算符,相应的,运算符通常用于指数运算。在ECMAScript2016,引入了来代替Math.pow

//Instead of..
Math.pow(7, 2) //49

//Use
7 ** 2 //49

ECMAScript 2017

1.Object.values()

Object.values()是一个新的函数与Object.keys()类似,但返回Object自身属性的所有值,不包括原型链中的任何值。

const cars = { BMW: 3, Tesla: 2, Toyota: 1 };
//ES2015
//Instead of ..
const vals = Object.keys(cars).map(key => cars[key]);
console.log(vals); //[3, 2, 1]

//ES2017
//Use ...
const values = Object.values(cars);
console.log(values); //[3, 2, 1]

2.Object.entries()

Object.entries()与Object.keys相关,但它返回的不仅是返回键,而是以数组的方式放回键和值。这使得在循环中使用对象或将对象转换为Maps等操作变的非常简单。

Example 1:

const cars = { BMW: 3, Tesla: 2, Toyota: 3 };
//ES 5.1
//Instead of extracting keys and then again looping
Object.keys(cars).forEach(function (key) {
     console.log(`key: ${key} value: ${cars[key]}`)
 })

//ECMAScript 2017 (ES8)
//Use Object.entries
for (let [key, value] of Object.entries(cars)) {
      console.log(`key: ${key} value: ${value}`);
 }

Example 2:

const cars = { 'BMW': 3, 'Tesla': 2, 'Toyota': 1 };
//ES2015
//Instead of..
//Get object keys add then add each item to Map in a loop
const map1 = new Map();
Object.keys(cars).forEach(key => {
      map1.set(key, cars[key]);
})
console.log(map1); ////Map { 'BMW' =>3, 'Tesla' => 2, 'Toyota' => 1 }

//ES2017 
//Use...
const map = new Map(Object.entries(cars));
console.log(map);

3.字符串填充

两个实例方法添加到String中--String.
prototype.padStart和String.prototype.padEnd--允许将空字符串或其它字符串附加/前置到原始字符串的开头或结尾。

'someString'.padStart(numberOfCharcters [,stringForPadding])
'5'.padStart(10) // '          5'
'5'.padStart(10, '=*') //'=*=*=*=*=5'
'5'.padEnd(10, '=*') //'5=*=*=*=*='

4.Async/Await

async关键字关键字告诉JavaScript编译器以不同的方式处理函数。只要到达该函数中的await关键字,编译器就会暂停。它假定await之后的表达式返回一个promise并等待,直到promise被resolved或rejected才执行下一步。
在下面的示例中,getAmount函数正在调用两个异步函数getUser和getBankBalance。使用promise可以做到这点,但是使用async await更加优雅和简单。

//Instead of..
//ES2015 Promise
function getAmount(userId) {
         getUser(userId)
             .then(getBankBalance)
             .then(amount => {
                console.log(amount)
           })
  }

//Use..
//ES2017
 async function getAmount2(userId) {
        var user = await getUser(userId);
        var amount = await getBankBalance(user);
        console.log(amount);
  }

 getAmount('1'); //$1, 000
 getAmount2('1'); //$1, 000

 function getUser(userId) {
        return new Promise(resolve => {
               setTimeout(() => {
                  resolve('john');
              }, 1000)
          })
 }

  function getBankBalance(user) {
           return new Promise((resolve, reject) => {
              setTimeout(() => {
                if (user == 'john') {
                     resolve('$1, 000');
                 } else {
                     reject('unknown user');
                 }
              }, 1000)
         })
   }          

4.1 Async函数返回一个Promise

如果你正在等待异步函数的结果,则需要使用Promise的then语法来捕获其结果。
在下面的这个例子中,我们想使用console.log但不在doubleAndAdd中console.log所以我们想使用then语法将结果传递给console.log。

//Async functions themselves return a promise!
       async function doubleAndAdd(a, b) {
          a = await doubleAfter1Sec(a);
          b = await doubleAfter1Sec(b);
          return a + b;
 }

//Usage:
doubleAndAdd(1, 2).then(console.log);

function doubleAfter1Sec(param) {
      return new Promise(resolve => {
          setTimeout(resolve(param * 2), 1000)
         })
}

4.2 同时调用async/await

在前面的例子中,我等待两次,每次等待1s.然而,我们可以并行调用,因为a和b不使用Promise.all的相互依赖。

async function doubleAndAdd(a, b) {
    //Notice that I'm using Promise.all
    //Also notice the use of Array destructuring! to capture the 
    //result
    [a, b] = await Promise.all([doubleAfter1Sec(a),doubleAfter1Sec(b)]);
            return a + b;
}

 //Usage:
 doubleAndAdd(1, 2).then(console.log);

 function doubleAfter1Sec(param) {
    return new Promise(resolve => {
          setTimeout(resolve(param * 2), 1000)
        })
 }

ECMAScript 2018

1.对象的rest属性

rest运算符...(三个点)允许我们提取尚未提取的Object属性。
你可以使用rest来帮助仅提取所需的属性

 //Extract firstName and age
 //and store the rest of items in 'remaining' variable
 let { firstName, age, ...remaining } = {
       firstName: 'john',
       lastName: 'smith',
       age: 20,
       height: '5.10',
       race: 'martian',
  };
  firstName; //john
  age; //20
  remaining; // { lastName: 'smith',  height: '5.10', race: 'martian' }

2.对象的spread属性

spread属性看起来就像具有三个点的rest属性,但不同的是使用spread来创建(重组)新对象。

注意:spread运算符用于等号的右侧,而rest运算符用在等号的左侧
//Merge person and account objects
const person = { fName: 'john', age: 20 };
const account = { name: 'bofa', amount: '$1000' }

const personAndAccount = { ...person, ...account };
personAndAccount // { fName: 'john', age: 20, name: 'bofa', amount: '$1000' }

总结

暂时写这些,还有一个没写上,因为有一些没有常用,若后面发现有其它的,我再加上。嘻嘻。

参考链接

Here are examples of everything new in ECMAScript 2016,2017,and 2018 by rajaraodv

相关文章

此处评论已关闭