前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >ES2020新特性

ES2020新特性

作者头像
前端黑板报
发布2020-04-10 13:57:13
6370
发布2020-04-10 13:57:13
举报
文章被收录于专栏:前端黑板报前端黑板报

2020年4月2日,TC39确定了ES2020的新特性,虽然现在还是 candidate 阶段,需要等到 Ecma GA 的最后确认。按照惯例每年3月份在TC39委员会上,Stage 4的特性会被确定,新的语法特性已被认可;也就是说,因为Stage 4的特性都是确定会作为新版特性发布的,所以基本上在每年3月份的时候,当前年度版本的新特性已经确定下来了。4月份-7月份为ECMA CC、ECMA GA复审阶段,7月份ECMA General Assembly批准新的标准,即在7月份当年份标准正式发布

V8打标签的新特性如下:

1.Dynamic import()

原生支持动态引入JavaScript文件,不需要借助Webpack和Babel,此特性可以实现按需加载就像现在的 code splittinig 功能。可以在 if-else 语句里面引入代码。

Dynamic import() 返回的是 promise 所以和 async/await 配合使用:

代码语言:javascript
复制
// math.js

const add = (num1, num2) => num1 + num2;
    
export { add };
代码语言:javascript
复制
// index.js
const doMath = async (num1, num2) => {
  if (num1 && num2) {
    const math = await import('./math.js');
    console.log(math.add(5, 10));
  };
};

doMath(4, 2);

详见:https://v8.dev/features/dynamic-import

2.BigInt

在 BigInt 之前,有最大安全整数:

代码语言:javascript
复制
const max = Number.MAX_SAFE_INTEGER;
// → 9_007_199_254_740_991

当我们加法运算时:

代码语言:javascript
复制
max + 1;
// → 9_007_199_254_740_992

是我们的预期结果,可是当我们加2时:

代码语言:javascript
复制
max + 2;
// → 9_007_199_254_740_992

并不是我们所期望的结果,居然是和加1时结果一样。也就是任何的整数运算如果超过了安全范围(Number.MIN_SAFE_INTEGER to Number.MAX_SAFE_INTEGER),所以为了解决这个问题BigInt就出现了。那如何把一个整数转换为BigInt,两种方法:

1. BigInt(123) 2. 123n

在计算一下上面的问题:

代码语言:javascript
复制
BigInt(Number.MAX_SAFE_INTEGER) + 2n;
// → 9_007_199_254_740_993n

注意:BigInt的值不能和其他的值直接做运算,需要显示类型转换。

一切其它例子:

类型:

代码语言:javascript
复制
typeof 123n;
// → 'bigint'

比较:

代码语言:javascript
复制
42n === BigInt(42);
// → true
42n == 42;
// → true
42n === 42
// → false

if-else

代码语言:javascript
复制
if (0n) {
  console.log('if');
} else {
  console.log('else');
}
// → logs 'else', because `0n` is falsy.

详见:https://v8.dev/features/bigint

3.Module namespace exports

JavaScript 模块之前就有下面的语法:

代码语言:javascript
复制
import * as utils from './utils.mjs';

可是一直没有对应的导出语法,所以2020加上了:

代码语言:javascript
复制
export * as utils from './utils.mjs';

等同于下面:

代码语言:javascript
复制
import * as utils from './utils.mjs';
export { utils };

详见:https://v8.dev/features/module-namespace-exports

4.String.prototype.matchAll

相比于之前的math提供了更多的信息:

math:

代码语言:javascript
复制
const string = 'Magic hex numbers: DEADBEEF CAFE';
const regex = /\b\p{ASCII_Hex_Digit}+\b/gu;
for (const match of string.match(regex)) {
  console.log(match);
}

// Output:
//
// 'DEADBEEF'
// 'CAFE'

matchAll:

代码语言:javascript
复制
const string = 'Magic hex numbers: DEADBEEF CAFE';
const regex = /\b\p{ASCII_Hex_Digit}+\b/gu;
let match;
while (match = regex.exec(string)) {
  console.log(match);
}

// Output:
//
// [ 'DEADBEEF', index: 19, input: 'Magic hex numbers: DEADBEEF CAFE' ]
// [ 'CAFE',     index: 28, input: 'Magic hex numbers: DEADBEEF CAFE' ]

详见:https://v8.dev/features/string-matchall

5:Promise.allSettled

这个Promise的静态方法类似 jQuery 的 done,只给出 promise 已经结束并需要知道成功、失败。适用的例子就是请求接口结束后,不管成败与否移出 loading 样式:

代码语言:javascript
复制
const promises = [
  fetch('/api-call-1'),
  fetch('/api-call-2'),
  fetch('/api-call-3'),
];
// Imagine some of these requests fail, and some succeed.

await Promise.allSettled(promises);
// All API calls have finished (either failed or succeeded).
removeLoadingIndicator();

详见:https://v8.dev/features/promise-combinators

6.globalThis

若之前你的代码既要在浏览器,也要在Nodejs同时也在 web-workers,获取 global 对象绝对是一件繁琐的事:

代码语言:javascript
复制
// A naive attempt at getting the global `this`. Don’t use this!
const getGlobalThis = () => {
  if (typeof globalThis !== 'undefined') return globalThis;
  if (typeof self !== 'undefined') return self;
  if (typeof window !== 'undefined') return window;
  if (typeof global !== 'undefined') return global;
  // Note: this might still return the wrong result!
  if (typeof this !== 'undefined') return this;
  throw new Error('Unable to locate global `this`');
};
const theGlobalThis = getGlobalThis();

所以ES2020给我带来了globalThis,不论在何种环境下执行代码它都代表全局对象:

代码语言:javascript
复制
global === window // true
global.setTimeout === window.setTimeout // true

详见:https://v8.dev/features/globalthis

7.Optional chaining

在JavaScript中获取嵌套的属性时容易产生错误,同时代码也冗长不易阅读:

代码语言:javascript
复制
// Error prone-version, could throw.
const nameLength = db.user.name.length;

// Less error-prone, but harder to read.
let nameLength;
if (db && db.user && db.user.name)
  nameLength = db.user.name.length;

那经过 Optional chaining 来更改一下:

代码语言:javascript
复制
// Still checks for errors and is much more readable.
const nameLength = db?.user?.name?.length;

上面的代码是不是简洁明了,那当db、user、name 是 null 或 undefined 时,nameLength 则会等于 undefined 而不是报错。若可以确定name始终存在且为字符串,则可以改成:

代码语言:javascript
复制
const nameLength = db?.user?.name.length

Optional chaining还有个优势,若 name 是空字符串,之前的写法会 nameLength 会得到 undefined,而新写法会得到 0。

8.Nullish coalescing

ES2020增加了一种新的处理默认值的短路求值特性。再说此属性之前,我们先回忆一下:&& 和 || ,它俩都是用来处理 truthy、falsy值的。在 JavaScript 中,null、undefined、false、0、NaN 和 '' 都代表假值,既然我们已经有&& 和 || 来处理了,那为何还要新增一个 ?? 呢?因为一些场景,它俩并不能优雅的处理:

代码语言:javascript
复制
function Component(props) {
  const enable = props.enabled || true;
  // …
}

当enabled没有设置时,也就是等于undefined时,我们给一个默认值true。可是当我们给 props.enabled 赋值为 false 时,结果并不是我们所希望的,当然此问题可以通过下面方法更改:

代码语言:javascript
复制
function Component(props) {
  const enable = props.enabled !== false;
  // …
}

可是此问题还是挺普遍,例如当 '' 和 0 就是期望值的时候,就像上面的 false 一样,所以为了解决此问题,引入了 ?? 特性。

代码语言:javascript
复制
function Component(props) {
  const enable = props.enabled ?? true;
  // …
}

?? 的左侧只处理 null 或 undefined ,效果和 || 类似:

代码语言:javascript
复制
false ?? true;   // => false
0 ?? 1;          // => 0
'' ?? 'default'; // => ''

null ?? [];      // => []
undefined ?? []; // => []

只有左侧的值为 null 或 undefined 时,才返回它右侧的值。

注意点:document.all 是一个类数组,返回页面上所有的节点但是在和 && 、|| 运算时得到的是 falsy,和 ?? 运算则不同。

代码语言:javascript
复制
document.all || true; // => true
document.all ?? true; // => HTMLAllCollection[]

详见:https://v8.dev/features/nullish-coalescing

本文参与 腾讯云自媒体分享计划,分享自微信公众号。
原始发表:2020-04-08,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 前端黑板报 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档