Javascript 在不同的环境获取全局对象有不通的方式,node 中通过 global, web中通过 window, self 等,有些甚至通过 this 获取,但通过 this 是及其危险的,this 在 js 中异常复杂,它严重依赖当前的执行上下文,这些无疑增加了获取全局对象的复杂性。
过去获取全局对象,可通过一个全局函数
var getGlobal = function () { if (typeof self !== 'undefined') { return self; } if (typeof window !== 'undefined') { return window; } if (typeof global !== 'undefined') { return global; } throw new Error('unable to locate global object'); }; var globals = getGlobal(); // https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/globalThis
而 globalThis 目的就是提供一种标准化方式访问全局对象,有了 globalThis 后,你可以在任意上下文,任意时刻都能获取到全局对象。
六:BigInt
Js 中 Number类型只能安全的表示-(2^53-1)至 2^53-1 范的值,即Number.MIN_SAFE_INTEGER 至Number.MAX_SAFE_INTEGER,超出这个范围的整数计算或者表示会丢失精度。
var num = Number.MAX_SAFE_INTEGER; // -> 9007199254740991 num = num + 1; // -> 9007199254740992 // 再次加 +1 后无法正常运算 num = num + 1; // -> 9007199254740992 // 两个不同的值,却返回了true 9007199254740992 === 9007199254740993 // -> true
为解决此问题,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)类型。
typeof 9007199254740993n; // -> 'bigint'
尽可能避免通过调用函数 BigInt 方式来实例化超大整型。因为参数的字面量实际也是 Number 类型的一次实例化,超出安全范围的数字,可能会引起精度丢失。
七:String.prototype.matchAll
思考下面代码
var str = '<text>JS</text><text>正则</text>'; var reg = /<\w+>(.*?)<\/\w+>/g; console.log(str.match(reg)); // -> ["<text>JS</text>", "<text>正则</text>"]
可以看出返回的数组里包含了父匹配项,但未匹配到子项(group)。移除全局搜索符“g”试试。
var str = '<text>JS</text><text>正则</text>'; // 注意这里没有全局搜素标示符“g” var reg = /<\w+>(.*?)<\/\w+>/; console.log(str.match(reg)); // 上面会打印出 /* [ "<text>JS</text>", "JS", index: 0, input: "<text>JS</text><text>正则</text>", groups: undefined ] */
这样可以获取到匹配的父项,包括子项(group),但只能获取到第一个满足的匹配字符。能看出上面无法匹配到<text>正则</text>。
如果获取到全局所有匹配项,包括子项呢?
ES2020提供了一种简易的方式:String.prototype.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 ] */
能看出每次迭代中可获取所有的匹配,以及本次匹配的成功的一些其他元信息。
参考资料
github.com/tc39/proposals/blob/master/finished-proposals.md
prop-tc39.now.sh/