浅谈目前可以使用ES10的5个新特性


Posted in Javascript onJune 25, 2019

ECMAScript 2015,也称为ES6,是一个花了6年时间完成的主要版本。从那时起,负责ECMAScript标准开发的技术委员会39 (TC39)每年都会发布该标准的新版本。这个年度发布周期简化了这个过程,并使新特性快速可用,JavaScript社区对此表示欢迎。

今年,ECMAScript 2019(简称ES2019)将会发布。 新功能包括Object.fromEntries(),trimStart(),trimEnd(),flat(),flatMap(),symbol对象的description属性,可选的catch绑定等。

好消息是这些功能已经在最新版本的Firefox和Chrome中实现,并且它们也可以被转换,以便旧版浏览器能够处理它们。

1. Object.fromEntries()

在JavaScript中,将数据从一种格式转换为另一种格式非常常见。 为了便于将对象转换为数组,ES2017引入了Object.entrie()方法。 此方法将对象作为参数,并以[key,value]的形式返回对象自己的可枚举字符串键控属性对的数组。 例如:

const obj = {one: 1, two: 2, three: 3};

console.log(Object.entries(obj));  
// => [["one", 1], ["two", 2], ["three", 3]]

但是如果我们想要做相反的事情并将键值对列表转换为对象呢? 某些编程语言(如Python)为此提供了dict()函数。 在Underscore.js和Lodash中还有_.fromPairs函数。

ES2019引入Object.fromEntries()方法为JavaScript带来类似的功能, 此静态方法允许你轻松地将键值对列表转换为对象:

const myArray = [['one', 1], ['two', 2], ['three', 3]];
const obj = Object.fromEntries(myArray);

console.log(obj);  // => {one: 1, two: 2, three: 3}

如你所见,Object.fromEntries()与Object.entries()所做的事情正好相反。 虽然以前可以实现Object.fromEntries()相同的功能,但它实现方式有些复杂:

const myArray = [['one', 1], ['two', 2], ['three', 3]];
const Array.from(myArray).reduce((acc, [key, val]) 
=> Object.assign(acc, {[key]: val}), {})

console.log(obj);  // => {one: 1, two: 2, three: 3}

请记住,传递给Object.fromEntries()的参数可以是实现可迭代协议的任何对象,只要它返回一个两元素,类似于数组的对象即可。

例如,在以下代码中,Object.fromEntries() 将Map对象作为参数,并创建一个新对象,其键和对应值由Map中的对给出:

const map = new Map();
map.set('one', 1);
map.set('two', 2);

const obj = Object.fromEntries(map);

console.log(obj);  // => {one: 1, two: 2}

Object.fromEntries() 方法对于转换对象也非常有用,思考以下代码:

const obj = {a: 4, b: 9, c: 16};

// 将对象转换为数组
const arr = Object.entries(obj);

// 计算数字的平方根
const map = arr.map(([key, val]) => [key, Math.sqrt(val)]);

// 将数组转换回对象
const obj2 = Object.fromEntries(map);

console.log(obj2); // => {a: 2, b: 3, c: 4}

上述代码将对象中的值转换为其平方根。 为此,它首先将对象转换为数组,然后使用map()方法获取数组中值的平方根,结果是可以转换回对象的数组。

使用Object.fromEntries()的另一种情况是处理URL的查询字符串,如本例所示

const paramsString = 'param1=foo¶m2=baz';
const searchParams = new URLSearchParams(paramsString);

Object.fromEntries(searchParams);  // => {param1: "foo", param2: "baz"}

此代码中,查询字符串将传递给 URLSearchParams()构造函数。 然后将返回值(即URLSearchParams对象实例)传递给Object.fromEntries() 方法,结果是一个包含每个参数作为属性的对象。

Object.fromEntries() 方法目前是第4阶段提案,这意味着它已准备好包含在ES2019标准中。

2. trimStart() and trimEnd()

trimStart()和trimEnd()方法在实现与trimLeft()和trimRight()相同。这些方法目前处于第4阶段,将被添加到规范中,以便与padStart()和padEnd()保持一致,来看一些例子:

const str = "  string  ";

// es2019
console.log(str.trimStart());  // => "string  "
console.log(str.trimEnd());   // => "  string"

// 相同结果
console.log(str.trimLeft());   // => "string  "
console.log(str.trimRight());  // => "  string"

对于Web兼容性,trimLeft() 和trimRight() 将保留为trimStart() 和trimEnd() 的别名。

3. flat() and flatMap()

flat() 方法可以将多维数组展平成一维数组

const arr = ['a', 'b', ['c', 'd']];
const flattened = arr.flat();

console.log(flattened);  // => ["a", "b", "c", "d"]

以前,我们经常使用reduce()或concat()来展平多维数组:

const arr = ['a', 'b', ['c', 'd']];
const flattend = [].concat.apply([], arr);

// or
// const flattened = [].concat(...arr);

console.log(flattened);  // => ["a", "b", "c", "d"]

请注意,如果提供的数组中有空值,它们会被丢弃:

const arr = ['a', , , 'b', ['c', 'd']];
const flattened = arr.flat();

console.log(flattened);  // => ["a", "b", "c", "d"]

flat() 还接受一个可选参数,该参数指定嵌套数组应该被展平的级别数。 如果未提供参数,则将使用默认值1:

const arr = [10, [20, [30]]];

console.log(arr.flat());   // => [10, 20, [30]]
console.log(arr.flat(1));  // => [10, 20, [30]]
console.log(arr.flat(2));  // => [10, 20, 30]

flatMap() 方法将map()和flat()组合成一个方法。 它首先使用提供的函数的返回值创建一个新数组,然后连接该数组的所有子数组元素。 来个例子:

const arr = [4.25, 19.99, 25.5];

console.log(arr.map(value => [Math.round(value)]));  
// => [[4], [20], [26]]

console.log(arr.flatMap(value => [Math.round(value)]));  
// => [4, 20, 26]

数组将被展平的深度级别为1.如果要从结果中删除项目,只需返回一个空数组:

const arr = [[7.1], [8.1], [9.1], [10.1], [11.1]];

// do not include items bigger than 9
arr.flatMap(value => {
 if (value >= 10) {
  return [];
 } else {
  return Math.round(value);
 }
}); 

// returns:
// => [7, 8, 9]

除了正在处理的当前元素外,回调函数还将接收元素的索引和对数组本身的引用。flat()和flatMap()方法目前处于第4阶段。

4.Symbol 对象的 description 属性

在创建Symbol时,可以为调试目的向其添加description (描述)。有时候,能够直接访问代码中的description 是很有用的。

ES2019 中为Symbol对象添加了只读属性 description ,该对象返回包含Symbol描述的字符串。

let sym = Symbol('foo');
console.log(sym.description);  // => foo

sym = Symbol();
console.log(sym.description);  // => undefined

// create a global symbol
sym = Symbol.for('bar');
console.log(sym.description);  // => bar

5.可选的 catch

try catch 语句中的catch有时候并没有用,思考下面代码:

try {
 // 使用浏览器可能尚未实现的功能
} catch (unused) {
 // 这里回调函数中已经帮我们处理好的错误
}

此代码中的catch回调的信息并没有用处。 但这样写是为了避免SyntaxError错误。 ES2019可以省略catch周围的括号:

try {
 // ...
} catch {
 // ....
}

另外:ES2020 的 String.prototype.matchAll

matchAll() 方法是ES2020 第4阶段提议,它针对正则表达式返回所有匹配(包括捕获组)的迭代器对象。

为了与match()方法保持一致,TC39 选择了“matchAll”而不是其他建议的名称,例如 “matches” 或 Ruby的 “scan”。看个简单的例子:

const re = /(Dr\. )\w+/g;
const str = 'Dr. Smith and Dr. Anderson';
const matches = str.matchAll(re);

for (const match of matches) {
 console.log(match);
}

// logs:
// => ["Dr. Smith", "Dr. ", index: 0, input: "Dr. Smith and Dr. Anderson", groups: undefined]
// => ["Dr. Anderson", "Dr. ", index: 14, input: "Dr. Smith and Dr. Anderson", groups: undefined]

此正则表达式中的捕获组匹配字符“Dr”,后跟一个点和一个空格。\w+ 匹配任何单词字符一次或多次。 并且g标志指示引擎在整个字符串中搜索模式。

之前,必须在循环中使用exec()方法来实现相同的结果,这不是非常有效:

const re = /(Dr\.) \w+/g;
const str = 'Dr. Smith and Dr. Anderson';
let matches;

while ((matches = re.exec(str)) !== null) {
 console.log(matches);
}

// logs:
// => ["Dr. Smith", "Dr.", index: 0, input: "Dr. Smith and Dr. Anderson", groups: undefined]
// => ["Dr. Anderson", "Dr.", index: 14, input: "Dr. Smith and Dr. Anderson", groups: undefined]

重要的是要注意尽管match() 方法可以与全局标志g一起使用来访问所有匹配,但它不提供匹配的捕获组或索引位置。 比较以下代码:

const re = /page (\d+)/g;
const str = 'page 2 and page 10';

console.log(str.match(re));  
// => ["page 2", "page 10"]

console.log(...str.matchAll(re)); 
// => ["page 2", "2", index: 0, input: "page 2 and page 10", groups: undefined] 
// => ["page 10", "10", index: 11, input: "page 2 and page 10", groups: undefined]

总结

在这篇文章中,我们仔细研究了 ES2019 中引入的几个关键特性,包括Object.fromEntries(),trimStart(), trimEnd(), flat(), flatMap(),symbol 对象的description 属性以及可选的catch 。

尽管一些浏览器还没有完全实现这些特性,但可以使用Babel和其他JavaScript转换器,仍然可以在项目中使用它们。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
根据判断浏览器类型屏幕分辨率自动调用不同CSS的代码
Feb 22 Javascript
jQuery powerFloat万能浮动层下拉层插件使用介绍
Dec 27 Javascript
JavaScript高级程序设计 阅读笔记(十三) js定义类或对象
Aug 14 Javascript
ajax中get和post的说明及使用与区别
Dec 23 Javascript
js onclick事件传参讲解
Nov 06 Javascript
javascript实现锁定网页、密码解锁效果(类似系统屏幕保护效果)
Aug 15 Javascript
javascript实现的一个随机点名功能
Aug 26 Javascript
Angular2 PrimeNG分页模块学习
Jan 14 Javascript
JavaScript中concat复制数组方法浅析
Jan 20 Javascript
Vue表单控件绑定图文详解
Feb 11 Javascript
vue.js中ref和$refs的使用及示例讲解
Aug 14 Javascript
详解为什么Vue中不要用index作为key(diff算法)
Apr 04 Javascript
vue 移动端注入骨架屏的配置方法
Jun 25 #Javascript
基于vue+axios+lrz.js微信端图片压缩上传方法
Jun 25 #Javascript
新手快速入门微信小程序组件库 iView Weapp
Jun 24 #Javascript
前端Vue项目详解--初始化及导航栏
Jun 24 #Javascript
微信小程序调用天气接口并且渲染在页面过程详解
Jun 24 #Javascript
微信小程序-可移动菜单的实现过程详解
Jun 24 #Javascript
webpack自动打包和热更新的实现方法
Jun 24 #Javascript
You might like
用session做客户验证时的注意事项
2006/10/09 PHP
PHP中Date获取时间不正确怎么办
2008/06/05 PHP
php print EOF实现方法
2009/05/21 PHP
同台服务器使用缓存APC效率高于Memcached的演示代码
2010/02/16 PHP
PHP 中检查或过滤IP地址的实现代码
2011/11/27 PHP
解析web文件操作常见安全漏洞(目录、文件名检测漏洞)
2013/06/29 PHP
PHP中使用FFMPEG获取视频缩略图和视频总时长实例
2014/05/04 PHP
PHP实现的MongoDB数据库操作类分享
2014/05/12 PHP
PHP函数http_build_query使用详解
2014/08/20 PHP
PHP使用Http Post请求发送Json对象数据代码解析
2020/07/16 PHP
JavaScript之引用类型介绍
2012/08/10 Javascript
基于iframe实现类似于ajax的页面无刷新
2014/05/31 Javascript
JQuery动态添加和删除表格行的方法
2015/03/09 Javascript
AngularJs IE Compatibility 兼容老版本IE
2016/09/01 Javascript
BootStrap selectpicker后台动态绑定数据的方法
2017/07/28 Javascript
Bootstrap一款超好用的前端框架
2017/09/25 Javascript
原生JS封装_new函数实现new关键字的功能
2018/08/12 Javascript
AngularJS实现的自定义过滤器简单示例
2019/02/02 Javascript
使用node搭建自动发图文微博机器人的方法
2019/03/22 Javascript
JavaScript数值类型知识汇总
2019/11/17 Javascript
JS实现可以用键盘方向键控制的动画
2020/12/11 Javascript
Vue实现一种简单的无限循环滚动动画的示例
2021/01/10 Vue.js
[03:55]DOTA2完美大师赛选手传记——LFY.MONET
2017/11/18 DOTA
[47:50]Secret vs VP 2018国际邀请赛小组赛BO2 第二场 8.17
2018/08/20 DOTA
python文件名和文件路径操作实例
2017/09/29 Python
Python获取当前公网ip并自动断开宽带连接实例代码
2018/01/12 Python
Django 开发环境与生产环境的区分详解
2019/07/26 Python
python pprint模块中print()和pprint()两者的区别
2020/02/10 Python
python实现猜单词游戏
2020/05/22 Python
详解Flask前后端分离项目案例
2020/07/24 Python
python如何将图片转换素描画
2020/09/08 Python
Python Charles抓包配置实现流程图解
2020/09/29 Python
修复iPhone的safari浏览器上submit按钮圆角bug
2012/12/24 HTML / CSS
葡萄牙鞋子品牌:Fair
2016/12/10 全球购物
努力学习演讲稿
2014/05/10 职场文书
暑期家教宣传单
2015/07/14 职场文书