ES2020的js新特性
1. 可选链
可选链,?.操作符,在访问属性或方法时,若存在为空的中间量,则返回undefined,在长链条的属性访问时,可节省代码
const stu = { name: 'xiaoming', school: { name: "xxx" } } const cityName = stu.address?.city?.name //cityName: undefined const res = stu.someMethod?.() //res: undefined
在可选链不能用的情况下,可以用lodash的get方法代替:
_.get(stu, 'adderss.city.name', 'default name');
2. 空值合并运算符
空值合并,??操作符,可以避开null和undefined,得到一个默认值。相比于a || b这种操作,对0、NaN等值不会转化为false,只处理null和undefined,规避了一些有效值
const foo = null ?? 'default' //foo: 'default' const baz = 0 ?? 12 //baz: 0
3. 管道运算符
|>操作符,类似于linux的管道,可以串行的执行函数
const double = (n) => n * 2; const increment = (n) => n + 1; double(increment(double(double(5)))); // 42 //使用管道操作符 5 |> double |> double |> increment |> double; // 42
4. 私有变量
在变量前加#,可以定义私有变量,仅能在类内部使用
class Message { #message = "Howdy" greet() { console.log(this.#message) } } const greeting = new Message() greeting.greet() // Howdy console.log(greeting.#message) // Private field '#message' must be declared in an enclosing class
5. Promise.allSettled
Promise.all的缺陷是,有一个任务reject,所有的任务都挂掉,这通常不是我们想要的结果。
Promise.allSettled,就是为了解决这个问题。它执行完后,返回所有的执行结果,无论是resolve还是reject,在放在一个数组里返回
Promise.allSettled([ Promise.reject({code: 500, msg: '服务异常'}), Promise.resolve({ code: 200, list: []}), Promise.resolve({code: 200, list: []}) ]) .then((ret) => { /* 0: {status: "rejected", reason: {…}} 1: {status: "fulfilled", value: {…}} 2: {status: "fulfilled", value: {…}} */ // 过滤掉 rejected 状态,尽可能多的保证页面区域数据渲染 RenderContent(ret.filter((el) => { return el.status !== 'rejected'; }));
6. 动态导入(Dynamic Import)
动态的import一个模块,返回一个promise,可以在module加载完成后做一些事情,或者捕获错误
el.onclick = () => { import(`/path/current-logic.js`) .then((module) => { module.doSomthing(); }) .catch((err) => { // load error; }) }
7. Top-level await
通常await只能在async函数中使用,新提案中,允许在顶层调用await,简化模块加载调用,可以和dynamic import配合使用
const strings = await import(`/i18n/${navigator.language}`); let jQuery; try { jQuery = await import('https://cdn-a.example.com/jQuery'); } catch { jQuery = await import('https://cdn-b.example.com/jQuery'); }
8. BigInt
ES2020提供一种新的数据类型:BigInt。使用 BigInt 有两种方式:
//在整数字面量后面加n。 var bigIntNum = 9007199254740993n; //使用 BigInt 函数。 var bigIntNum = BigInt(9007199254740); var anOtherBigIntNum = BigInt('9007199254740993'); //通过 BigInt, 我们可以安全的进行大数整型计算 var bigNumRet = 9007199254740993n+ 9007199254740993n; // -> -> 18014398509481986n bigNumRet.toString(); // -> '18014398509481986'
BigInt 是一种新的数据原始(primitive)类型。
typeof9007199254740993n; // -> 'bigint'
9. String.prototype.matchAll
//有g,匹配到所有项,但是未显示匹配的group var str = '<text>JS</text><text>正则</text>'; var reg = /<\w+>(.*?)<\/\w+>/g; console.log(str.match(reg)); // -> ["<text>JS</text>", "<text>正则</text>"] //无g,只匹配到第一项,这回显示了匹配的group var str = '<text>JS</text><text>正则</text>'; var reg = /<\w+>(.*?)<\/\w+>/; console.log(str.match(reg)); // 上面会打印出 /* [ "<text>JS</text>", "JS", index: 0, input: "<text>JS</text><text>正则</text>", groups: undefined ] */
matchAll解决的就是,既能匹配出所有项,也能得到每项的详细信息,例如group的匹配, matchAll, 会返回一个迭代器
var str = '<text>JS</text><text>正则</text>'; var allMatchs = str.matchAll(/<\w+>(.*?)<\/\w+>/g); for(const match of allMatchs) { console.log(match); } /* 第一次迭代返回: [ "<text>JS</text>", "JS", index: 0, input: "<text>JS</text><text>正则</text>", groups: undefined ] 第二次迭代返回: [ "<text>正则</text>", "正则", index: 15, input: "<text>JS</text><text>正则</text>", groups: undefined ] */
会得到匹配到的所有项,及其详细信息。