在写本文时,本文提到的新的 JavaScript 提案功能已进入第 4 阶段,并且几乎肯定会包含在 ES2021 中。你已经可以开始在 最新版本的浏览器,Node.js 和 Babel 中使用。

注意:ECMAScript 是 JavaScript 所基于的标准,由 TC39 委员会管理。ECMAScript 始终是一个不需要的名称,这会使一切都对初学者感到困惑。人们经常谈论 JavaScript 功能,但参考的是 ECMAScript 规范。

更新特性

  • 数字分隔符(_

  • 逻辑分配(&&=||=??=

  • 引用不足(WeakRefFinalizationRegistry

  • Promise.any

  • String.prototype.replaceAll

1. 数值分隔符

大数字文字很难使人眼快速解析,尤其是当有很多重复的数字时:

1000000000000   1019436871.42

为了提高可读性,新的 JavaScript 语言功能 启用了下划线作为数字文字中的分隔符。因此,上面的内容现在可以重写为每千位数字,例如:

1_000_000_000_000    1_019_436_871.42

现在,更容易说出第一个数字是 1 万亿,而第二个数字大约是 10 亿。

数字分隔符有助于提高各种数字文字的可读性:

// A decimal integer literal with its digits grouped per thousand:
1_000_000_000_000
// A decimal literal with its digits grouped per thousand:
1_000_000.220_720
// A binary integer literal with its bits grouped per octet:
0b01010110_00111000
// A binary integer literal with its bits grouped per nibble:
0b0101_0110_0011_1000
// A hexadecimal integer literal with its digits grouped by byte:
0x40_76_38_6A_73
// A BigInt literal with its digits grouped per thousand:
4_642_473_943_484_686_707n

它们甚至适用于八进制整数文字(尽管 我想不出 其中分隔符为此类文字提供值 的示例):

// A numeric separator in an octal integer literal: ????‍♀️
0o123_456

请注意,JavaScript 还具有不带显式 0o 前缀的八进制文字的旧式语法。例如,017 === 0o17。在严格模式下或模块内不支持此语法,并且在现代代码中不应使用此语法。因此,这些文字不支持数字分隔符。使用 0o17 风格的文字代替。

2. Promise combinators

自从 ES2015 中引入 Promise 以来,JavaScript 完全支持两种 Promise 组合器:静态方法 Promise.all 和 Promise.race。

目前有两个新提案正在通过标准化流程:Promise.allSettled 和 Promise.any。有了这些添加,JavaScript 中将总共有四个诺言组合器,每个组合器支持不同的用例。

以下是这四个组合器的概述:

2.1 Promise.allSettled

Promise.allSettled 给你当所有输入的诺言是一种信号结算,这意味着他们要么履行或拒绝。如果您不在乎承诺的状态,而只是想知道工作何时完成,无论它是否成功,这都是很有用的。

例如,您可以启动一系列独立的 API 调用,并使用 Promise.allSettled 它们来确保它们已全部完成,然后再执行其他操作,例如删除加载微调器:

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();

2.2 Promise.any

Promise.any 方法和 Promise.race 类似——只要给定的迭代中的一个 promise 成功,就采用第一个 promise 的值作为它的返回值,但与 Promise.race 的不同之处在于——它会等到所有 promise 都失败之后,才返回失败的值:

const promises = [fetch('/endpoint-a').then(() => 'a'),fetch('/endpoint-b').then(() => 'b'),fetch('/endpoint-c').then(() => 'c'),
];
try {const first = await Promise.any(promises);// Any of the promises was fulfilled.console.log(first);// → e.g. 'b'
} catch (error) {// All of the promises were rejected.console.assert(error instanceof AggregateError);// Log the rejection values:console.log(error.errors);// → [//     <TypeError: Failed to fetch /endpoint-a>,//     <TypeError: Failed to fetch /endpoint-b>,//     <TypeError: Failed to fetch /endpoint-c>//   ]
}

此代码示例检查哪个端点响应最快,然后将其记录下来。只有当 所有 请求都失败时,我们才最终进入代码 catch 块,然后在其中处理错误。

Promise.any 拒绝可以一次代表多个错误。为了在语言级别支持此功能,引入了一种新的错误类型,称为 AggregateError。除了上面示例中的基本用法外,还可以以编程方式构造 AggregateError 对象,就像其他错误类型一样:

const aggregateError = new AggregateError([errorA, errorB, errorC], 'Stuff went wrong!');

3. Weak references and finalizers

此功能包含两个高级对象 WeakRefFinalizationRegistry。根据使用情况,这些接口可以单独使用,也可以一起使用。正确使用它们需要仔细考虑,如果可能,最好避免使用它们。

一般来说,在JavaScript中,对象的引用是强保留的,这意味着只要持有对象的引用,它就不会被垃圾回收。

const ref = { x: 42, y: 51 };
// 只要我们访问 ref 对象(或者任何其他引用指向该对象),这个对象就不会被垃圾回收

目前在 Javascript 中,WeakMap 和 WeakSet 是弱引用对象的唯一方法:将对象作为键添加到 WeakMap 或 WeakSet 中,是不会阻止它被垃圾回收的。

JavaScript 的 WeakMap 并不是真正意义上的弱引用:实际上,只要键仍然存活,它就强引用其内容。WeakMap 仅在键被垃圾回收之后,才弱引用它的内容。

WeakRef 是一个更高级的 API,它提供了真正的弱引用,Weakref 实例具有一个方法 deref,该方法返回被引用的原始对象,如果原始对象已被收集,则返回 undefined 对象。

JavaScript 中对象的引用是强引用,WeakMap 和 WeakSet 可以提供部分的弱引用功能,若想在 JavaScript 中实现真正的弱引用,可以通过配合使用 WeakRef 和终结器(Finalizer)来实现。

WeakRef 是用来指目标对象不脱离垃圾收集保留它的对象。如果未通过垃圾回收回收目标对象,则 WeakRefs 可以取消引用以允许访问目标对象。

// Create a WeakRef object referring to a given target object
const ref = new WeakRef(targetObject)// Return the WeakRef instance's target object, or undefined if the target object has been garbage-collected
const obj = ref.deref()

使用 FinalizationRegistry 对象可以在垃圾回收对象时请求回调。

// Create a registry object that uses the given callback
const registry = new FinalizationRegistry([callback])// Register an object with a registry instance so that if the object is garbage-collected, the registry's callback may get called
registry.register(target, heldValue, [unregisterToken])// Unregister a target object from a registry instance
registry.unregister(unregisterToken)

更多信息:TC39提案,V8

4. String.prototype.replaceAll

当前,如果不使用全局正则表达式,就无法替换字符串中子字符串的所有实例。与字符串参数一起使用时,String.prototype.replace 仅影响首次出现。

String.prototype.replaceAll() 将为开发人员提供一种简单的方法来完成此常见的基本操作。

'aabbcc'.replaceAll('b', '.') // 'aa..cc'
'aabbcc'.replaceAll(/b/g, '.') // 'aa..cc'

5. Logical assignment (逻辑分配)

支持与新的运营逻辑分配 &&=||=??=。与它们的 数学和按位对应物不同,逻辑分配遵循其各自逻辑操作的短路行为。仅当逻辑运算将评估右侧时,它们才执行分配。

// falsy: false, 0, -0, 0n, "", null, undefined, and NaN
// truthy: all values are truthy unless defined as falsy
// nullish: null or undefineda ||= b
// Logical OR assignment
// Equivalent to: a || (a = b);
// Only assigns if a is falsya &&= b
// Logical AND assignment
// Equivalent to: a && (a = b);
// Only assigns if a is truthya ??= b
// Logical nullish assignment
// Equivalent to: a ?? (a = b);
// Only assigns if a is nullish

5.1 具体例子

带有 && 运算符的逻辑赋值运算符

仅当 LHS 值为真时,才将 RHS 变量值赋给 LHS 变量。

// Logical Assignment Operator with && operator
let num1 = 5
let num2 = 10
num1 &&= num2
console.log(num1) // 10
// Line 5 can also be written as following ways
// 1. num1 && (num1 = num2)
// 2. if (num1) num1 = num2

带有 || 的运算符逻辑赋值运算符

仅当 LHS 值为假时,才将 RHS 变量值赋给 LHS 变量。

// Logical Assignment Operator with || operator
let num1
let num2 = 10
num1 ||= num2
console.log(num1) // 10
// Line 5 can also be written as following ways
// 1. num1 || (num1 = num2)
// 2. if (!num1) num1 = num2

带有 ?? 运算符的逻辑赋值运算符

ES2020 引入了空值合并运算符,其也可以与赋值运算符结合使用。仅当 LHS 为 undefined 或仅为 null 时,才将 RHS 变量值赋给 LHS 变量。

// Logical Assignment Operator with ?? operator
let num1
let num2 = 10
num1 ??= num2
console.log(num1) // 10
num1 = false
num1 ??= num2
console.log(num1) // false
// Line 5 can also be written as following ways
// num1 ?? (num1 = num2)

概括

作为开发人员,跟紧语言的新特性是很重要的。

以上将在 2021 年发布的一些新功能,它们是进入第 4 阶段的提案,几乎可以肯定会包括在内,这些功能已经在最新的浏览器和 babel 中实现。

参考文章:JavaScript Features in 2021

可以加猫哥的 wx:CB834301747 ,一起闲聊前端。

微信搜 “全栈修炼”,回复 “电子书” 即可以获得 300 本前端精华书籍哦。

往期精文

  • Vue3 全家桶 + Element Plus + Vite + TypeScript + Eslint 项目配置最佳实践

  • TypeScript 中提升幸福感的 10 个高级技巧

  • 推荐 7 个 Vue2、Vue3 源码解密分析的重磅开源项目

通过阅读本篇文章,如果有收获的话,可以点个赞在看,这将会成为我持续分享的动力,感谢~

JavaScript ES2021 最值得期待的 5 个新特性解析相关推荐

  1. 最值得期待的 5 个新特性解析JavaScript ES2021

    最值得期待的 5 个新特性解析JavaScript ES2021 [url]https://m.hongxiu.com/so/%E6%96%B0%E7%89%88%E6%9F%A5%E5%B0%94% ...

  2. JavaScript ES2021 新特性解析

    JavaScript ES2021 新特性解析 新特性列表 String.prototype.replaceAll Promise.any 逻辑运算符和赋值表达式 数值分隔符 Intl.ListFor ...

  3. 美监管“叫停”BUSD!是时候了解一下值得期待的几个新DeFi 稳定币了

    这是白话区块链的第1861期原创 作者 | 五火球教主 出品|白话区块链(ID:hellobtc) 最近稳定币再次站上了风口浪尖. 原因不外乎BUSD的发行机构Paxos被NYDFS查水表,结果一纸政 ...

  4. 探索 webpack5 新特性 Module federation 引发的javascript共享模块变革

    webpack5 新特性 Module federation 引言 什么是Module federation "模块联邦" Module federation "模块联邦 ...

  5. Kotlin 1.4 和未来值得期待的地方

    对于企业来说,目前的Android开发面临着许多挑战,尤其是选择哪种技术用于开发最好的Android应用程序. Kotlin和Java是用于Android应用程序开发的两种编程语言,即使是有技术背景的 ...

  6. 2018,这些重大科技值得期待

    图①:"悟空"暗物质科学实验卫星示意图. 中国科学院供图 图②:北斗卫星模型图. <script type="text/javascript"> / ...

  7. 列一下09年值得期待的20部影片(轻松一把)

    08年是电影承前启后的一年,虽然没有07年<变形金刚>,<加三>,<蜘蛛侠3>,<哈利5>等的大片井喷的辉煌,但是却出现了沉寂十余年创造IMDB奇迹的& ...

  8. audio 上一首 下一首 自定义样式_我们的歌:盛典即将来临,勤深深还有一首歌,这场表演值得期待...

    在最新一期<我们的歌>节目里面,勤深深回归,并且唱了一首歌曲<爱情转移>粤语版<富士山下>. 虽然回归让人惊喜,但是很显然,对于喜欢勤深深的歌迷来说,一首歌曲,是不 ...

  9. # 日期待t_2020最值得期待的几款新车

    2019年,对于中国乘用车企来说充满着艰难与挑战:跨越之后,迎来变数后的新2020,这是一个开始,也是新挑战的延续.那么在新的一年之初,不妨提前看看几款最值得期待的新家伙,或许有那么一个就是你的&qu ...

最新文章

  1. 一文了解迁移学习经典算法
  2. JS获取当天零点或23:59:59的时间
  3. python + MySql 基本操作
  4. 捡到vivo手机怎么清除账号_大学保安两天两次跳湖为路人捡手机,您怎么看?...
  5. checkbox和radio的样式美化问题
  6. SAP Spartacus 服务器端渲染调试的开发端版本
  7. CSS之Bootstrap(快速布局)
  8. 【转】OAuth的改变
  9. flash cs4中3D特性之PerspectiveProjection属性设置
  10. lockdir便携式文件夹加密器(单文件绿色版)
  11. 638-字符串模式匹配-KMP算法
  12. 基于深度学习的CNN边缘检测RCF--Richer Convolutional Features for Edge Detection
  13. 试图运行项目时出错:未能加载文件或程序集 或它的某一个依赖项。该模块应包含一个程序集清单 .
  14. 从起步到影响世界:漫谈韩国网游发展史
  15. 场景编程集锦 - 吉米的总统梦想
  16. Flutter中ListView顶部有空白
  17. uni微信小程序引入商圈快速积分插件
  18. 体验TiDB V6.0.0 之Clinic
  19. 正念,探寻自我觉醒之路(深度想考)
  20. GO/KEGG富集分析泡泡图中为什么基因的数目是小数?

热门文章

  1. C++之Lambda表达式
  2. linux tomcat 日志路径,linux日志文件在哪 linux安装tomcat
  3. linux系统配置php环境,linux下php环境的搭建
  4. css中 media的用法,如何在css中正确使用@media
  5. java joda 获取utc时间_java – 使用JodaTime以毫秒为单位的UTC到本地时间
  6. tensorflow随笔-tf.group
  7. Github热榜--《程序员做饭指南》
  8. 【学术相关】研究生哪些行为可以在导师那超加分?你做到了吗?
  9. 目前最全:52 个深度学习目标检测模型汇总,论文、源码一应俱全!
  10. 2020年搜索推荐系统论文干货集锦