[译] ES2018(ES9)的新特性

原文链接:https://www.sitepoint.com/es2018-whats-new/
在本文中,我将介绍通过ES2018(ES9)引入的JavaScript的新功能,以及它们的用途以及如何使用它们的示例。

JavaScript(ECMAScript)是一个不断发展的标准,由多个平台上的许多供应商实现。ES6(ECMAScript 2015)是一个大型版本,花了六年时间才完成。新的年度发布流程已经制定,以简化流程并更快地添加功能。ES9(ES2018)是撰写本文时的最新版本。

技术委员会39(TC39)由包括浏览器供应商在内的各方组成,他们在严格的推进路径上推动JavaScript提案:

  • Stage 0: strawman——最初想法的提交。

  • Stage 1: proposal(提案)——由TC39至少一名成员倡导的正式提案文件,该文件包括API事例。

  • Stage 2: draft(草案)——功能规范的初始版本,该版本包含功能规范的两个实验实现。

  • Stage 3: candidate(候选)——提案规范通过审查并从厂商那里收集反馈

  • Stage 4: finished(完成)——提案准备加入ECMAScript,但是到浏览器或者Nodejs中可能需要更长的时间

ES2016

ES2016通过添加两个小功能证明了标准化过程:

  1. 数组包含()方法,当数组中包含值时返回true或false,以及
  2. 运算符,与...相同。a ** b Math.pow(a, b)

ES2017

ES2017提供了更多的新功能:

  • 异步函数可实现更清晰的Promise语法
  • Object.values() 从包含名称 - 值对的对象中提取值数组
  • Object.entries(),返回包含对象中名称和值的子数组数组
  • Object.getOwnPropertyDescriptors()返回的对象限定为另一个对象的自己的属性属性描述符(.value.writable,,,,).get``.set``.configurable``.enumerable
  • padStart()和,字符串填充的两个元素padEnd()
  • 对象定义,数组声明和函数参数列表的尾随逗号
  • SharedArrayBuffer以及Atomics读取和写入共享内存位置(为响应Spectre漏洞而禁用)。

有关更多信息,请参阅ES2017中的新增功能

ES2018

ECMAScript 2018(或ES9,如果您更喜欢旧的表示法)现已推出。以下功能已达到第4阶段,但在编写本文时,浏览器和运行时的工作实现将不完整。

异步迭代

在异步/等待过程中的某个时刻,您将尝试在同步循环内调用异步函数。例如:

async function process(array) {
  for (let i of array) {
    await doSomething(i);
  }
}

它不会起作用。这也不会:

async function process(array) {
  array.forEach(async i => {
    await doSomething(i);
  });
}

循环本身保持同步,并且总是在它们的内部异步操作之前完成。

ES2018引入了异步迭代器,它与常规迭代器一样,只是方法返回一个Promise。因此,关键字可以与循环一起使用以串行运行异步操作。例如:next()awaitfor … of

async function process(array) {
  for await (let i of array) {
    doSomething(i);
  }
}

Promise.finally()

Promise链可以成功并达到最终或失败并触发阻止。在某些情况下,无论结果如何,您都希望运行相同的代码 - 例如,清理,删除对话框,关闭数据库连接等。.then().catch()

该 原型允许你指定一个地方的最终逻辑,而不是在最后的复制它和:.finally().then().catch()

function doSomething() {
  doSomething1()
  .then(doSomething2)
  .then(doSomething3)
  .catch(err => {
    console.log(err);
  })
  .finally(() => {
    // finish here!
  });
}

Rest/Spread 属性

ES2015引入了Rest参数扩展运算符。三个点(...)仅用于数组。Rest参数语法允许我们将一个布丁数量的参数表示为一个数组。

restParam(1, 2, 3, 4, 5);

function restParam(p1, p2, ...p3) {
  // p1 = 1
  // p2 = 2
  // p3 = [3, 4, 5]
}

spread运算符以相反的方式工作,并将数组转换为可以传递给函数的单独参数。例如,给定任意数量的参数,返回最高值:Math.max()

const values = [99, 100, -1, 48, 16];
console.log( Math.max(...values) ); // 100

ES2018为对象解构提供了和数组一样的Rest参数()和展开操作符,一个简单的例子:

const myObject = {
  a: 1,
  b: 2,
  c: 3
};

const { a, ...x } = myObject;
// a = 1
// x = { b: 2, c: 3 }

或者您可以使用它将值传递给函数:

restParam({
  a: 1,
  b: 2,
  c: 3
});

function restParam({ a, ...x }) {
  // a = 1
  // x = { b: 2, c: 3 }
}

跟数组一样,Rest参数只能在声明的结尾处使用。此外,它只适用于每个对象的顶层,如果对象中潜逃对象则无法适用。

扩展运算符可以在其他对象内使用,例如:

const obj1 = { a: 1, b: 2, c: 3 };
const obj2 = { ...obj1, z: 26 };
// obj2 is { a: 1, b: 2, c: 3, z: 26 }

您可以使用spread运算符来克隆对象(),但请注意,您只能获得浅拷贝。如果属性包含另一个对象,则克隆将引用同一对象。obj2 = { ...obj1 };

正则表达式命名捕获组(Regular Expression Named Capture Groups)

JavaScript正则表达式可以返回匹配对象 - 类似于数组的值,包含匹配的字符串。例如,要以YYYY-MM-DD格式解析日期:

const
  reDate = /([0-9]{4})-([0-9]{2})-([0-9]{2})/,
  match  = reDate.exec('2018-04-30'),
  year   = match[1], // 2018
  month  = match[2], // 04
  day    = match[3]; // 30

它很难阅读,并且更改正则表达式也可能会更改匹配对象索引。

ES2018允许在开始捕获括号后立即使用符号命名组。例如:?<name>(

const
  reDate = /(?<year>[0-9]{4})-(?<month>[0-9]{2})-(?<day>[0-9]{2})/,
  match  = reDate.exec('2018-04-30'),
  year   = match.groups.year,  // 2018
  month  = match.groups.month, // 04
  day    = match.groups.day;   // 30

任何未匹配的命名组都将其属性设置为undefined。

命名捕获也可用于方法中。例如,将日期转换为美国MM-DD-YYYY格式:replace()

const
  reDate = /(?<year>[0-9]{4})-(?<month>[0-9]{2})-(?<day>[0-9]{2})/,
  d      = '2018-04-30',
  usDate = d.replace(reDate, '$<month>-$<day>-$<year>');

正则表达式反向断言(lookbehind)

JavaScript目前支持正则表达式中的前瞻断言。这意味着必须进行匹配但不捕获任何内容,并且断言不包含在整个匹配的字符串中。例如,要从任何价格中捕获货币符号:

const
  reLookahead = /\D(?=\d+)/,
  match       = reLookahead.exec('$123.89');

console.log( match[0] ); // $

ES2018引入以相同方式工作但是匹配前面的反向断言(lookbehind),这样我就可以忽略货币符号,单纯的捕获价格的数字:

const
  reLookbehind = /(?<=\D)\d+/,
  match        = reLookbehind.exec('$123.89');

console.log( match[0] ); // 123.89

以上是 肯定反向断言,非数字\D必须存在。同样的,还存在 否定反向断言,表示一个值必须不存在,例如:

const
  reLookbehindNeg = /(?<!\D)\d+/,
  match           = reLookbehind.exec('$123.89');

console.log( match[0] ); // null
正则表达式dotAll模式

正则表达式中点.匹配除回车外的任何单字符,标记s改变这种行为,允许行终止符的出现,例如:

/hello.world/s.test('hello\nworld'); // true
正则表达式Unicode属性转义

到目前为止,还无法在正则表达式中本机访问Unicode字符属性。ES2018添加了Unicode属性转义 - 在表单和- 中设置了(unicode)标志的正则表达式。例如:\p{...}\P{...}u

const reGreekSymbol = /\p{Script=Greek}/u;
reGreekSymbol.test('π'); // true

模板文字调整

最后,删除了与模板文字中的转义序列相关的所有语法限制。

之前,\u开始一个 unicode 转义,\x开始一个十六进制转义,\后跟一个数字开始一个八进制转义。这使得创建特定的字符串变得不可能,例如Windows文件路径 C:\uuu\xxx\111。更多细节参考模板字符串

这就是ES2018,但是ES2019的工作已经开始了。你有什么特色想要明年看到吗?

译者参考

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 214,904评论 6 497
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 91,581评论 3 389
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 160,527评论 0 350
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 57,463评论 1 288
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,546评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,572评论 1 293
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,582评论 3 414
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,330评论 0 270
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,776评论 1 307
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,087评论 2 330
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,257评论 1 344
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,923评论 5 338
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,571评论 3 322
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,192评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,436评论 1 268
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,145评论 2 366
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,127评论 2 352

推荐阅读更多精彩内容